Categories
Vue 3

Vue 3 — v-for

Vue 3 is in beta and it’s subject to change.

Vue 3 is the up and coming version of Vue front end framework.

It builds on the popularity and ease of use of Vue 2.

In this article, we’ll look at rendering arrays and objects with v-for .

v-if with v-for

We shouldn’t use v-if and v-for together.

This is because v-for renders everything and then v-if checks every item whether they need to be rendered.

Instead, we should filter out the items beforehand with computed properties and use that with v-for .

When they’re used together, v-for has higher priority over v-if .

List Rendering

We can render an array of items onto the screen with v-for .

For example, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div v-for="p in people">
        {{ p.name }}
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            people: [{ name: "mary" }, { name: "james" }, { name: "jane" }]
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

to render the items in the people array onto the screen.

We use the v-for directive to loop through each entry and render each item onto the screen.

We can also get the index of the item by writing:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg._com_/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div v-for="(p, index) in people">
        {{index}} - {{ p.name }}
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            people: [{ name: "mary" }, { name: "james" }, { name: "jane" }]
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

Then we get the index of the item with index.

We used in to loop through the array, but we can replace in with of to make it resemble the for-of loop:

<div v-for="p of people"></div>

v-for with an Object

v-for also works for objects.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div v-for="value in obj">
        {{value}}
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            obj: {
              james: 20,
              mary: 30,
              jane: 10
            }
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

to loop through the values of an object and display each value.

To get the key, we can add a second parameter to the loop:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div v-for="(value, name) in obj">
        {{name}}: {{value}}
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            obj: {
              james: 20,
              mary: 30,
              jane: 10
            }
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

name has the key of the object.

The 3rd item in the comma-separated list is the index:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div v-for="(value, name, index) in obj">
        {{index}} - {{name}}: {{value}}
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            obj: {
              james: 20,
              mary: 30,
              jane: 10
            }
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

Conclusion

We can render objects and arrays with the v-for directive.

Categories
Vue 3

Vue 3 — More About v-model

Vue 3 is in beta and it’s subject to change.

Vue 3 is the up and coming version of Vue front end framework.

It builds on the popularity and ease of use of Vue 2.

In this article, we’ll look at how to use the Vue 3 v-model directive.

Multiple Select

Select elements that let us do multiple selections work with the v-model directive.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <select v-model="selected" multiple>
        <option disabled value="">Please select one</option>
        <option>apple</option>
        <option>orange</option>
        <option>grape</option>
      </select>
      <p>{{ selected }}</p>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            selected: []
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

We have the select element which has the multiple attribute.

The selected variable is a variable instead of a string since it can contain multiple values.

v-model is bound to the selected array so that Vue can get all the selected values and put it in the array.

Now when we choose multiple options from the select box, we can see all of them in an array.

Dynamic Options

We can add dynamic options in the select element.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <select v-model="selected">
        <option disabled value="">Please select one</option>
        <option v-for="option in options" :value="option.value">
          {{ option.text }}
        </option>
      </select>
      <p>{{ selected }}</p>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            selected: [],
            options: [
              { value: "apple", text: "apple" },
              { value: "orange", text: "orange" },
              { value: "grape", text: "grape" }
            ]
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

to render the options with the v-for directive.

option.value is used as the value of each option .

and option.text is used as the value of each text entry.

Value Bindings

Radio buttons and select elements are bound to string with v-model .

Checkboxes are bound to boolean values.

We can use the v-bind directive to bind to types of values that are different from the default.

For example, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <input
        type="checkbox"
        v-model="toggle"
        true-value="yes"
        false-value="no"
      />
      <p>{{ toggle }}</p>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            toggle: ""
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

We added the true-value and false-value props so that the checkbox bind to those values instead of a boolean.

So true is 'yes' and false is 'no' .

That’s what we’ll see when we click the checkbox.

We can do the same thing with radio buttons.

For example, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <input type="radio" v-model="selected" :value="apple" />
      <label>apple</label>
      <input type="radio" v-model="selected" :value="orange" />
      <label>orange</label>
      <p>{{ selected }}</p>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return { selected: "", apple: "apple", orange: "orange" };
        }
      }).mount("#app");
    </script>
  </body>
</html>

We dynamically bound the value with the :value directive instead of setting the value statically.

Since v-model of both radio buttons are set to the same value, we can select between them.

Then their value will be displayed.

Conclusion

Many kinds of form controls work with the v-model directive.

Also, we can bind to their values in different ways.

Categories
Vue 3

Vue 3 — Keyboard and Mouse

Vue 3 is in beta and it’s subject to change.

Vue 3 is the up and coming version of Vue front end framework.

It builds on the popularity and ease of use of Vue 2.

In this article, we’ll look at how to handle key and mouse events in Vue 3 components.

Key Modifiers

Vue 3 can handle keyboard events.

For instance, we can write:

<input @keyup.enter="submit" />

to run the submit method when the keyup event is triggered by pressing the enter key.

Any valid key name is acceptable as the modifier.

The following key aliases can also be used as modifiers:

  • .enter
  • .tab
  • .delete (captures both "Delete" and "Backspace" keys)
  • .esc
  • .space
  • .up
  • .down
  • .left
  • .right

System Modifier Keys

We can also add modifiers for system modifier keys like Alt and Ctrl.

We can use the following as modifiers:

  • .ctrl
  • .alt
  • .shift
  • .meta

The meta key is the Windows key on Windows keyboards.

On Sun keyboards, it’s the diamond key.

And on Macs, it’s the command key.

So we can listen to the Ctrl + Enter key combo press on an element by writing:

<input @keyup.ctrl.enter="clear" />

We can also listen to Ctrl + click by writing:

<div @click.ctrl="onCtrlClick">ctrl + click me</div>

.exact Modifier

The .exact modifier lets us control the exact combination of system modifiers needed to trigger an event.

For example, if we have:

<button @click.ctrl="onClick">click me</button>

then if alt or shift is pressed, then onClick will also be run.

However, if we have:

<button @click.ctrl.exact="onCtrlClick">A</button>

Then onCtrlClick only runs when we Ctrl + click the button.

Mouse Button Modifiers

Vue 3 also provides modifiers for mouse buttons.

They are:

  • .left
  • .right
  • .middle

for listening to the presses of specific buttons.

Listeners in HTML

Listeners in HTML frees the component code including DOM logic, which is cleaner than having them all in JavaScript.

When the view model is destroyed, all event listeners are automatically removed.

Form Input Bindings

We can use the v-model directive to bind the input value to the state property.

It’s syntactic sugar for updating data on user input events.

v-model ignores the initial value , checked , or selected attributes found in any element.

Only the state in the Vue instances is treated as the source of truth.

Therefore, we should remove those attributes and just set the initial value in the Vue instance.

v-model internally uses different properties and emit different events for different input elements.

Text inputs use value property and input event.

Checkboxes and radio buttons use the checked property and change event.

Select fields use the value as a prop and change as an event.

To use the v-model directive, we can write:

<!DOCTYPE html>  
<html lang="en">  
  <head>  
    <title>App</title>  
    <script src="https://unpkg.com/vue@next"></script>  
  </head>  
  <body>  
    <div id="app">  
      <input v-model="message" placeholder="message" />  
      <p>{{ message }}</p>  
    </div>  
    <script>  
      const vm = Vue.createApp({  
        data() {  
          return {  
            message: ""  
          };  
        }  
      }).mount("#app");  
    </script>  
  </body>  
</html>

We returned an object with the message property so that we can use it with v-model .

Then we render the value of message to show what we entered.

v-model will automatically synchronize the input value and the value of message .

Therefore, when we type something in the box, it’ll be displayed below it.

Conclusion

We can listen to key and mouse events with v-on .

v-model binds the inputted value to the Vue instance state.

Categories
Vue 3

Vue 3 — Inline Styles and v-if

Vue 3 is in beta and it’s subject to change.

Vue 3 is the up and coming version of Vue front end framework.

It builds on the popularity and ease of use of Vue 2.

In this article, we’ll look at inline style bindings and v-if.

Binding Inline Styles

There’re various ways to bind inline styles to an element.

One way is to pass in an object to the :style directive.

For example, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div :style="{ color, fontSize: `${fontSize}px` }">
        hello
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            color: "red",
            fontSize: 30
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

We have the color and fontSize properties in the object we return in the data method.

Then we used that in the object we use as the value of the :style directive.

So ‘hello’ should be red and 30px in size.

We can replace that with an object to make the template shorter.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div :style="styleObj">
        hello
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            styleObj: {
              color: "red",
              fontSize: "30px"
            }
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

There’s also an array syntax to let us add multiple style objects to the same element.

For example, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div :style="[baseStyles, overridingStyles]">
        hello
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            baseStyle: {
              color: "red",
              fontSize: "30px"
            },
            overridingStyles: {
              color: "green"
            }
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

We have the baseStyles and overridingStyles in one array.

The styles in overridingStyles will override the styles in baseStyle completely.

So we get that the text is green and it’s in its default size.

If browser-specific prefixes are needed, then they’ll be added automatically.

We can also provide an array of values to a style property with an array.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div :style="{ display: ['-webkit-box', '-ms-flexbox', 'flex'] }">
        hello
      </div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {};
        }
      }).mount("#app");
    </script>
  </body>
</html>

We have all the variants of flex in the array.

Conditional Rendering

We can add conditional rendering with the v-if directive.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <button @click="on = !on">toggle</button>
      <h1 v-if="on">hello world!</h1>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            on: true
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

We have the on property returned with the object we return indata , so we can use it with v-if to conditionally render the h1 element.

Also, we have a button to toggle on between true or false so that we’ll see the h1 toggled on and off as we click the button.

Conclusion

Inline styles can be added with the :style directive.

It takes an object or an array.

We can use v-if to conditionally render an element.

Categories
Vue 3

Vue 3 — HTML and Directives

Vue 3 is the up and coming version of Vue front end framework.

It builds on the popularity and ease of use of Vue 2.

In this article, we’ll look at how to create templates with Vue 3.

Raw HTML

We can render raw HTML with the v-html directive.

For example, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <p>{{ rawHtml }}</p>
      <p><span v-html="rawHtml"></span></p>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            rawHtml: `<b>foo</b>`
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

We have the rawHtml property returned with the object we return in the data method.

If we pass raw HTML into the mustache, it’ll be sanitized. This means the raw code will be displayed.

If we pass it into the v-html directive, it’ll be displayed as HTML, so it’ll be bold.

Therefore, if we use v-html , we should be careful of cross-site scripting vulnerabilities.

We should only display trusted content with v-html .

Attributes

If we want to set attribute values dynamically, we’ve to use the v-bind directive.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <div v-bind:id="dynamicId"></div>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            dynamicId: `foo`
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

to set the id attribute of the div to foo by using v-bind .

If we have boolean attributes, its existence means we set the value totrue .

For example, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <button v-bind:disabled="disabled">Button</button>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            disabled: true
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

We disabled the button by passing in the disabled value to v-bind:disabled , which is true .

JavaScript Expressions

We can put JavaScript expressions between the double curly braces.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      {{message.split('').reverse().join('')}}
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            message: "hello world"
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

to reverse 'hello world' in the template.

We can only put in single expressions and not statements, so we can’t write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      {{ var a = 1 }}}
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            message: "hello world"
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

The Vue template compiler will give us an error.

Directives

Directives are special attributes that starts with v- .

The values they expect are single JavaScript expressions.

v-for and v-on are exceptions to this.

We reactively apply the side effects to the DOM when the value of its expression changes.

For instance, we can write:

<!DOCTYPE html>
<html lang="en">
  <head>
    <title>App</title>
    <script src="https://unpkg.com/vue@next"></script>
  </head>
  <body>
    <div id="app">
      <p v-if="show">hello world</p>
    </div>
    <script>
      const vm = Vue.createApp({
        data() {
          return {
            show: true
          };
        }
      }).mount("#app");
    </script>
  </body>
</html>

to show the ‘hello world’ message with v-if since show is true .

v-if is a directive that shows something when its value is truthy.

Conclusion

Templates can have raw HTML, attributes, and directives.

Directives are special attributes that take values.