Example ui-dimmer component with login form

HTML

<div id="app">
  <button class="ui button" @click="onShow">
    Login
  </button>
  <login :open="visible" @hide="onHide">
  </login>
</div>

<template id="ui-dimmer">
  <div class="ui dimmer" ref="dimmer" :class="className" @click="close">
    <div class="content">
      <div ref="dimmerOutside" class="center">
        <slot></slot>
      </div>
    </div>
  </div>
</template>

<template id="login">
  <ui-dimmer :active="open" @hide="$emit('hide')" closable>
    <div class="ui container login-form">
      <h2 class="ui teal image header">
        <div class="content">
          Log-in to your account
        </div>
      </h2>
      <form class="ui large form" @submit.prevent="onSubmit">
        <div class="ui stacked segment">
          <div class="field">
            <div class="ui left icon input">
              <i class="user icon"></i>
              <input type="text" name="email" placeholder="E-mail address">
            </div>
          </div>
          <div class="field">
            <div class="ui left icon input">
              <i class="lock icon"></i>
              <input type="password" name="password" placeholder="Password">
            </div>
          </div>
          <button class="ui fluid large teal submit button">Login</button>
        </div>

        <div class="ui error message"></div>

      </form>

      <div class="ui message">
        New to us? <a href="#">Sign Up</a>
      </div>
    </div>
  </ui-dimmer>
</template>

CSS

@import url('https://unpkg.com/[email protected]/semantic.css');

@media (min-width: 786px) {
  .ui.container.login-form {
    max-width: 450px !important;
  }
}

JavaScript

Vue.component('ui-dimmer', {
	name: 'ui-dimmer',
  template: '#ui-dimmer',
  props: {
    page: {
      type: Boolean,
      default: false
    },
    active: {
      type: Boolean,
      default: false
    },
    closable: {
    	type: Boolean,
      default: false
    }
  },
  mounted() {
    if (this.active) {
      this.show()
    }
  },
  computed: {
    className() {
      let classes = []

      return classes
    }
  },
  data() {
  	return {
    	visible: false
    }
  },
  watch: {
    active(val) {
      if (val) {
        this.show()
      } else {
        this.hide()
      }
    }
  },
  methods: {
    close($event) {
      if ($event && $event.target == this.$refs.dimmerOutside) {
      	if (this.closable && this.visible) {
      		console.log('click outside')
    			
        }
      }
    },
    show() {
      const dimmer = this.$refs.dimmer

      if (this.page) {
        document.body.classList.add('dimmed', 'dimmable')
        dimmer.classList.add('page')
      }

      dimmer.classList.add('active', 'transition', 'visible')
      this.visible = true
    },
    hide() {
      const dimmer = this.$refs.dimmer

      if (this.page) {  document.body.classList.remove('dimmed', 'dimmable')
        dimmer.classList.remove('page')
      }

      dimmer.classList.remove('active', 'transition', 'visible')
      this.visible = false
    }
  }
})

Vue.component('login', {
	name: 'login',
  template: '#login',
  props: {
  	open: Boolean
  },
  methods: {
    onSubmit() {
    	alert('login onSubmit')
    	this.$emit('hide')
    }
  }
})

new Vue({
	el: '#app',
  data: {
  	visible: false
  },
  methods: {
  	onShow() {
    	this.visible = true
    },
  	onHide() {
    	this.visible = false
    }
  }
})