完成角色添加UI

完成角色添加UI

<template>

      尽量不要删除用户组～删除用户组会造成用户组混乱！请谨慎编辑。

          角色名称
          显示名称
          描述
          更新时间
          操作

          {{ role.name }}
          {{ role.display_name }}
          {{ role.description }}
          {{ role.updated_at }}

            <button type="button" class="btn btn-primary btn-sm">管理</button>

            <button v-if="deleteIds.hasOwnProperty(role.id)" type="button" class="btn btn-danger btn-sm" disabled="disabled">

            </button>
            <button v-else type="button" class="btn btn-danger btn-sm" @click.prevent="deleteRole(role.id)">删除</button>

              <input v-model="add.name" type="text" class="form-control" placeholder="输入角色名称">

              <input v-model="add.display_name" type="text" class="form-control" placeholder="输入显示名称">

              <input v-model="add.description" type="text" class="form-control" placeholder="输入节点描述">

            <button v-if="add.adding" class="btn btn-primary btn-sm" disabled="disabled">

            </button>
            <button v-else type="button" class="btn btn-primary btn-sm" @click.pervent="postPerm">添加</button>

</template>

<template>

      尽量不要删除用户组～删除用户组会造成用户组混乱！请谨慎编辑。

          节点名称
          显示名称
          描述
          更新时间
          操作

          {{ role.name }}
          {{ role.display_name }}
          {{ role.description }}
          {{ role.updated_at }}

            <button type="button" class="btn btn-primary btn-sm">管理</button>

            <button v-if="deleteIds.hasOwnProperty(role.id)" type="button" class="btn btn-danger btn-sm" disabled="disabled">

            </button>
            <button v-else type="button" class="btn btn-danger btn-sm" @click.prevent="deleteRole(role.id)">删除</button>

</template>


camp form ref css

camp form ref css

remp/remp#207

<template>

                                    Edit campaign

                                    Create campaign

                                {{ name }}

We've developed a single process for freelancers with proven industry expirience to access the best projects from clients that use additional services on Workspace.

                                    Campaign name & primary banner (required)

                                                Name
                                                <input v-model="name" class="form-control fg-input" name="name" id="name" type="text">

                                                        Banner

                                                        <v-select v-model="bannerId"
                                                                id="banner_id"
                                                                :name="'banner_id'"
                                                                :value="bannerId"
                                                                :options.sync="bannerOptions"
                                                        ></v-select>

                                    A/B test

                                                        Banner B alternative

                                                        <v-select v-model="altBannerId"
                                                                id="alt_banner_id"
                                                                :name="'alt_banner_id'"
                                                                :value="altBannerId"
                                                                :title="'No alternative'"
                                                                :options.sync="altBannerOptions"
                                                        ></v-select>

                                    Segments - who will see the banner?

User needs to be member of all selected segments for campaign to be shown.

                                                        User signed-in state

                                                        <v-select v-model="signedIn"
                                                                id="signed_in"
                                                                :name="'signed_in'"
                                                                :value="signedIn"
                                                                :options.sync="signedInOptions"
                                                                :title="'Everyone'"
                                                        ></v-select>
                                                        To use this filter, you have to be setting signedIn: Boolean within your REMP tracking code.

                                                        <select v-model="addedSegment" title="Select user segments" v-on:change="selectSegment" class="selectpicker" data-live-search="false">
                                                            <optgroup v-for="(list,label) in availableSegments" v-bind:label="label">
                                                                <option v-for="(obj,code) in list" v-bind:value="obj">
                                                                    {{ obj.name }}
                                                                </option>
                                                            </optgroup>
                                                        </select>

                                                Active user segments

                                            <input type="hidden" v-bind:name="'segments['+i+'][id]'" v-model="segment.id" />
                                            <input type="hidden" v-bind:name="'segments['+i+'][code]'" v-model="segment.code" />
                                            <input type="hidden" v-bind:name="'segments['+i+'][provider]'" v-model="segment.provider" />

                                            <input type="hidden" name="removedSegments[]" v-model="removedSegments[i]" />

                                                        {{ segmentMap[segment.code] }}

                                                            ×

                                    Banner rules - how often to display?

                                <pageview-rules :pageviewRules="pageviewRules"></pageview-rules>

                                        Display once per session
                                        <input v-model="oncePerSession" value="1" name="once_per_session" type="checkbox">

                                    Geo targeting - which countries?

                                                Whitelist / Blacklist

                                                <v-select v-model="countriesBlacklist"
                                                        id="countries_blacklist"
                                                        :name="'countries_blacklist'"
                                                        :value="countriesBlacklist"
                                                        :options.sync="countriesBlacklistOptions"
                                                >
                                                </v-select>

                                                Countries

                                                <v-select v-model="countries"
                                                        id="countries"
                                                        :name="'countries[]'"
                                                        :value="countries"
                                                        :options.sync="availableCountries"
                                                        multiple
                                                >
                                                </v-select>

                                    Devices targeting (mobile/desktop)

                                        Show on {{ device }}
                                        <input :checked="deviceSelected(device)" :value="device" name="devices[]" type="checkbox">

                                    When to launch

                                                    Activate now

                                                    Add new schedule

                                                                Active
                                                                <input v-model="active" value="1" name="active" type="checkbox">

                                                                Activating campaign will create new schedule if there is none running.
Deactivating campaign will disable all running and planned schedules.

                                                            Planning new schedule activates campaign.

                                                                    Start time
                                                                    <input class="form-control date-time-picker" name="new_schedule_start_time_frontend" type="datetime" id="new_schedule_start_time_frontend">

                                                                <input name="new_schedule_start_time" type="hidden">

                                                                    End time
                                                                    <input class="form-control date-time-picker" name="new_schedule_end_time_frontend" type="datetime" id="new_schedule_end_time_frontend">

                                                                <input name="new_schedule_end_time" type="hidden">

                                            <input type="hidden" name="activation_mode" v-bind:value="activationMode" />

                        <button class="btn btn-info waves-effect" type="submit" name="action" value="save">
                             Save
                        </button>
                        <button class="btn btn-info waves-effect" type="submit" name="action" value="save_close">
                             Save and close
                        </button>

</template>


[gui] Add keyboard shortcut for opening files

<template>
  <v-app id="assembler" v-bind:dark="dark_mode">

    <v-navigation-drawer
      fixed
      mini-variant
      permanent
      app
    >
      <v-list two-line>
        <v-tooltip right>
          <v-list-tile slot="activator" @click="newFile('')">
            <v-list-tile-action>
              <v-icon large>note_add</v-icon>
            </v-list-tile-action>
          </v-list-tile>
          New File
        </v-tooltip>
        <v-tooltip right>
          <v-list-tile slot="activator" @click="saveFile()">
            <v-list-tile-action>
              <v-badge color="orange darken-2" overlap>
                <v-icon large>save</v-icon>
                !
              </v-badge>
            </v-list-tile-action>
          </v-list-tile>
          Save File
        </v-tooltip>
        <v-tooltip right>
          <v-list-tile slot="activator" @click="openFile()">
            <v-list-tile-action>
              <v-icon large>folder_open</v-icon>
            </v-list-tile-action>
          </v-list-tile>
          Open File
        </v-tooltip>
        <v-tooltip right>
          <v-list-tile slot="activator" @click="assemble()">
            <v-list-tile-action>
              <v-icon large>build</v-icon>
            </v-list-tile-action>
          </v-list-tile>
          Assemble
          Convert
          Assemble or Convert
        </v-tooltip>
      </v-list>
    </v-navigation-drawer>

    <v-content>
      <v-container fluid fill-height>
        <v-layout row wrap>
          <v-flex xs12 shrink class="editor-console-wrapper">

{{ getFilename }}

            <editor id="editor" class="elevation-2" v-model="editor.current_content" @init="editorInit" lang="lc3" v-bind:theme="dark_mode ? 'twilight' : 'textmate'" height="100%" width="98%"> </editor>

          </v-flex>
        </v-layout>
      </v-container>
    </v-content>

  </v-app>
</template>


inline recommendations filters

inline recommendations filters

<template>

       {{ $t('Filter') }}
      <button
        class="no-outline brdr-none py15 px40 bg-cl-mine-shaft :bg-cl-th-secondary ripple h5 cl-white sans-serif"
        @click="resetAllFilters"
        v-show="hasActiveFilters"
      >
        {{ $t('Clear') }}
      </button>

        {{ $t(filterIndex + '_filter') }}

        <color-selector
          context="category"
          code="color"
          v-for="(color, index) in filter"
          :key="index"
          :id="color.id"
          :label="color.label"
        />

        <size-selector
          context="category"
          code="size"
          class="size-select mr10 mb10"
          v-for="(size, index) in sortById(filter)"
          :key="index"
          :id="size.id"
          :label="size.label"
        />

        <price-selector
          context="category"
          class="price-select mb10 block"
          code="price"
          v-for="(price, index) in filter"
          :key="index"
          :id="price.id"
          :from="price.from"
          :to="price.to"
          :content="price.label"
        />

        <generic-selector
          context="category"
          class="mr10 mb10 block"
          :code="filterIndex"
          v-for="(option, index) in filter"
          :key="index"
          :id="option.id"
          :label="option.label"
        />

</template>

<template>

       {{ $t('Filter') }}
      <button
        class="no-outline brdr-none py15 px40 bg-cl-mine-shaft :bg-cl-th-secondary ripple h5 cl-white sans-serif"
        @click="resetAllFilters"
        v-show="hasActiveFilters"
      >
        {{ $t('Clear') }}
      </button>

        {{ $t(filterIndex + '_filter') }}

        <color-selector
          context="category"
          code="color"
          v-for="(color, index) in filter"
          :key="index"
          :id="color.id"
          :label="color.label"
        />

        <size-selector
          context="category"
          code="size"
          class="size-select mr10 mb10"
          v-for="(size, index) in sortById(filter)"
          :key="index"
          :id="size.id"
          :label="size.label"
        />

        <price-selector
          context="category"
          class="price-select mb10 block"
          code="price"
          v-for="(price, index) in filter"
          :key="index"
          :id="price.id"
          :from="price.from"
          :to="price.to"
          :content="price.label"
        />

        <generic-selector
          context="category"
          class="price-select mb10 block"
          :code="filterIndex"
          v-for="(option, index) in filter"
          :key="index"
          :id="option.id"
          :label="option.label"
        />

</template>


#649 - formatting

#649 - formatting

<template>

 0"
  >

          {{ heading }}

      <product-listing columns="4" :products="product.related[type]" />

</template>


chore: add disabled-date demo for date-picker

<template>

    <veui-date-picker>

非受控组件

    <veui-date-picker
      range
      clearable
    />

日期选择

    <veui-date-picker
      v-model="selectedDate"
      clearable
    />

日期范围选择

    <veui-date-picker
      v-model="selectedDateRange"
      clearable
      range
      format="MM/dd/yyyy"
    />

日期范围选择（快捷）

    <veui-date-picker
      v-model="selectedDateRange"
      range
      :shortcuts="shortcuts"
    />

月份选择

    <veui-date-picker
      v-model="selectedMonth"
      type="month"
    />

月份范围选择

    <veui-date-picker
      v-model="selectedMonthRange"
      type="month"
      range
    />

年份选择

    <veui-date-picker
      v-model="selectedYear"
      type="year"
    />

年份范围选择

    <veui-date-picker
      v-model="selectedYearRange"
      type="year"
      range
    />

小尺寸日期范围

    <veui-date-picker
      v-model="selectedDateRange"
      clearable
      range
      ui="s"
    />

小尺寸月份范围

    <veui-date-picker
      v-model="selectedDateRange"
      clearable
      range
      type="month"
      ui="s"
    />

小尺寸年份范围

    <veui-date-picker
      v-model="selectedDateRange"
      clearable
      range
      type="year"
      ui="s"
    />

禁用

      <veui-date-picker
        v-model="selectedDate"
        disabled
      />

禁用特定日期

      <veui-date-picker
        v-model="selectedDate"
        :disabled-date="disabledDate"
      />

invalid

      <veui-date-picker
        v-model="selectedDate"
        class="veui-invalid"
      />

范围禁用

      <veui-date-picker
        v-model="selectedDateRange"
        range
        disabled
      />

范围readonly

      <veui-date-picker
        v-model="selectedDateRange"
        range
        readonly
      />

      作用域插槽
      date

      <veui-date-picker
        v-model="selectedDateRange"
        range
      >
        <template
          slot="date"
          slot-scope="{ date }"
        >
          {{ date }}
        </template>
      </veui-date-picker>

可清除选择

      <veui-date-picker
        v-model="selectedDate"
        clearable
      />

可清除范围选择

      <veui-date-picker
        v-model="selectedDateRange"
        range
        clearable
      />

</template>

<template>

    <veui-date-picker>

非受控组件

    <veui-date-picker
      range
      clearable
    />

日期选择

    <veui-date-picker
      v-model="selectedDate"
      clearable
    />

日期范围选择

    <veui-date-picker
      v-model="selectedDateRange"
      clearable
      range
      format="MM/dd/yyyy"
    />

日期范围选择（快捷）

    <veui-date-picker
      v-model="selectedDateRange"
      range
      :shortcuts="shortcuts"
    />

月份选择

    <veui-date-picker
      v-model="selectedMonth"
      type="month"
    />

月份范围选择

    <veui-date-picker
      v-model="selectedMonthRange"
      type="month"
      range
    />

年份选择

    <veui-date-picker
      v-model="selectedYear"
      type="year"
    />

年份范围选择

    <veui-date-picker
      v-model="selectedYearRange"
      type="year"
      range
    />

小尺寸日期范围

    <veui-date-picker
      v-model="selectedDateRange"
      clearable
      range
      ui="s"
    />

小尺寸月份范围

    <veui-date-picker
      v-model="selectedDateRange"
      clearable
      range
      type="month"
      ui="s"
    />

小尺寸年份范围

    <veui-date-picker
      v-model="selectedDateRange"
      clearable
      range
      type="year"
      ui="s"
    />

禁用

      <veui-date-picker
        v-model="selectedDate"
        disabled
      />

invalid

      <veui-date-picker
        v-model="selectedDate"
        class="veui-invalid"
      />

范围禁用

      <veui-date-picker
        v-model="selectedDateRange"
        range
        disabled
      />

范围readonly

      <veui-date-picker
        v-model="selectedDateRange"
        range
        readonly
      />

      作用域插槽
      date

      <veui-date-picker
        v-model="selectedDateRange"
        range
      >
        <template
          slot="date"
          slot-scope="{ date }"
        >
          {{ date }}
        </template>
      </veui-date-picker>

可清除选择

      <veui-date-picker
        v-model="selectedDate"
        clearable
      />

可清除范围选择

      <veui-date-picker
        v-model="selectedDateRange"
        range
        clearable
      />

</template>


Tree: not check node when it's disabled (#11847)

<template>

 this.handleContextMenu($event)"
    v-show="node.visible"
    :class="{
      'is-expanded': expanded,
      'is-current': tree.store.currentNode === node,
      'is-hidden': !node.visible,
      'is-focusable': !node.disabled,
      'is-checked': !node.disabled && node.checked
    }"
    role="treeitem"
    tabindex="-1"
    :aria-expanded="expanded"
    :aria-disabled="node.disabled"
    :aria-checked="node.checked"
    :draggable="tree.draggable"
    @dragstart.stop="handleDragStart"
    @dragover.stop="handleDragOver"
    @dragend.stop="handleDragEnd"
    @drop.stop="handleDrop"
    ref="node"
  >

      <el-checkbox
        v-if="showCheckbox"
        v-model="node.checked"
        :indeterminate="node.indeterminate"
        :disabled="!!node.disabled"
        @click.native.stop
        @change="handleCheckChange"
      >
      </el-checkbox>

      <node-content :node="node"></node-content>

    <el-collapse-transition>

        <el-tree-node
          :render-content="renderContent"
          v-for="child in node.childNodes"
          :render-after-expand="renderAfterExpand"
          :key="getNodeKey(child)"
          :node="child"
          @node-expand="handleChildNodeExpand">
        </el-tree-node>

    </el-collapse-transition>

</template>


fix: Collapsible item should have text truncated

<template>

{{ label }}

      keyboard_arrow_down

      <slot></slot>

</template>


Fix Vue warning

Fix Vue warning

<template>
</template>

<script>
  export default {
    name: 'TableFixedTHead',
    methods: {
      handleScroll: function (event) {
        var table = document.getElementById('gs-table-fixed')

        if (table.length < 1) {
          console.error('[E] Table element #gs-table-fixed not found for fixed head feature')
          return
        }

        var tbody = table.getElementsByTagName('tbody')
        var tbodyHeight = 0
        var top = table.getBoundingClientRect()['top']
        var offsetX = table.getBoundingClientRect()['x']

        if (tbody.length > 0) {
          tbodyHeight = tbody[0].offsetHeight
        }

        if (top < 0 && -top + offsetX < tbodyHeight) {
          var thead = table.getElementsByClassName('gs-table-fixed-head')

          if (table.getElementsByClassName('gs-table-fixed-head').length < 1) {
            // Add fixed thead element
            var originalheader = table.getElementsByTagName('thead')[0]
            var newheader = document.createElement('thead')
            newheader.className = 'gs-table-fixed-head'
            newheader.innerHTML = originalheader.innerHTML
            table.appendChild(newheader)
          }

          thead = table.getElementsByClassName('gs-table-fixed-head')[0]

          var header = document.getElementsByTagName('header')
          var headerHeight = 0

          if (header.length > 0) {
            headerHeight = header[0].offsetHeight
          }

          thead.style.display = 'block'

          thead.style.top = -top + headerHeight + 'px'
        } else {
          if (table.getElementsByClassName('gs-table-fixed-head').length > 0) {
            table.getElementsByClassName('gs-table-fixed-head')[0].style.display = 'none'
          }
        }
      }
    },
    mounted: function () {
      window.addEventListener('scroll', this.handleScroll)
    },
    destroyed: function () {
      window.removeEventListener('scroll', this.handleScroll)
    }
  }
</script>


Fix style for description column header

Fix style for description column header

<template>

            {{ $t('assets.fields.episode') }}

          {{ $t('assets.fields.name') }}

            {{ $t('assets.fields.description') }}

            <button-simple
              class="is-small flexrow-item"
              icon="plus"
              :text="''"
              @click="onAddMetadataClicked"
              v-if="isCurrentUserAdmin && !isLoading"
            />

              {{ descriptor.name }}

              <chevron-down-icon
                @click="showMetadataHeaderMenu(descriptor.id, $event)"
                class="header-icon flexrow-item"
              />

            {{ $t('assets.fields.time_spent') }}

              <router-link
                class="flexrow-item validation-name"
                style="margin-right: 0;"
                :to="taskTypePath(columnId)"
              >
                {{ !hiddenColumns[columnId] ? taskTypeMap[columnId].name : '' }}
              </router-link>
              <chevron-down-icon
                @click="showHeaderMenu(columnId, $event)"
                class="header-icon flexrow-item"
              />

            <button-link
              :class="{
                'is-small': true,
                highlighted: isEmptyTask
              }"
              icon="plus"
              :text="$t('tasks.create_tasks')"
              :path="createTasksPath"
              v-if="isCurrentUserManager && displayedAssets.length > 0 && !isLoading"
            />

{{ $t('assets.empty_list') }}

    <button-link
      class="level-item big-button"
      :text="$t('assets.new_assets')"
      :path="newAssetPath()"
    />

{{ $t('assets.empty_list_client') }}

            {{ group[0] ? group[0].asset_type_name : '' }}

            {{ episodeMap[asset.episode_id] ? episodeMap[asset.episode_id].name : $t('main.all') }}

            <entity-thumbnail :entity="asset" />

            <router-link
              class="asset-link"
              :to="assetPath(asset.id)"
            >
              {{ asset.name }}
            </router-link>

          <description-cell
            class="description"
            v-if="!isCurrentUserClient && isShowInfos"
            :entry="asset"
          />

            {{ asset.data ? asset.data[descriptor.field_name] : '' }}

            {{ formatDuration(asset.timeSpent) }}

          <validation-cell
            :class="{
              'validation-cell': !hiddenColumns[columnId],
              'hidden-validation-cell': hiddenColumns[columnId]
            }"
            :key="columnId + '-' + asset.id"
            :ref="'validation-' + getIndex(i, k) + '-' + j"
            :column="taskTypeMap[columnId]"
            :entity="asset"
            :task-test="taskMap[asset.validations[columnId]]"
            :selected="assetSelectionGrid[getIndex(i, k)][j]"
            :rowX="getIndex(i, k)"
            :columnY="j"
            :minimized="hiddenColumns[columnId]"
            :is-static="true"
            :is-assignees="isShowAssignations"
            @select="onTaskSelected"
            @unselect="onTaskUnselected"
            v-for="(columnId, j) in sortedValidationColumns"
            v-if="!hiddenColumns[columnId] || isShowInfos"
          />
          <row-actions v-if="isCurrentUserManager"
            :entry="asset"
            :edit-route="editPath(asset.id)"
            :delete-route="deletePath(asset.id)"
            :restore-route="restorePath(asset.id)"
          />

    {{ displayedAssetsLength }} {{ $tc('assets.number', displayedAssetsLength) }}

</template>

<template>

            {{ $t('assets.fields.episode') }}

          {{ $t('assets.fields.name') }}

            {{ $t('assets.fields.description') }}
            <button-simple
              class="is-small"
              icon="plus"
              :text="''"
              @click="onAddMetadataClicked"
              v-if="isCurrentUserAdmin && !isLoading"
            />

              {{ descriptor.name }}

              <chevron-down-icon
                @click="showMetadataHeaderMenu(descriptor.id, $event)"
                class="header-icon flexrow-item"
              />

            {{ $t('assets.fields.time_spent') }}

              <router-link
                class="flexrow-item validation-name"
                style="margin-right: 0;"
                :to="taskTypePath(columnId)"
              >
                {{ !hiddenColumns[columnId] ? taskTypeMap[columnId].name : '' }}
              </router-link>
              <chevron-down-icon
                @click="showHeaderMenu(columnId, $event)"
                class="header-icon flexrow-item"
              />

            <button-link
              :class="{
                'is-small': true,
                highlighted: isEmptyTask
              }"
              icon="plus"
              :text="$t('tasks.create_tasks')"
              :path="createTasksPath"
              v-if="isCurrentUserManager && displayedAssets.length > 0 && !isLoading"
            />

{{ $t('assets.empty_list') }}

    <button-link
      class="level-item big-button"
      :text="$t('assets.new_assets')"
      :path="newAssetPath()"
    />

{{ $t('assets.empty_list_client') }}

            {{ group[0] ? group[0].asset_type_name : '' }}

            {{ episodeMap[asset.episode_id] ? episodeMap[asset.episode_id].name : $t('main.all') }}

            <entity-thumbnail :entity="asset" />

            <router-link
              class="asset-link"
              :to="assetPath(asset.id)"
            >
              {{ asset.name }}
            </router-link>

          <description-cell
            class="description"
            v-if="!isCurrentUserClient && isShowInfos"
            :entry="asset"
          />

            {{ asset.data ? asset.data[descriptor.field_name] : '' }}

            {{ formatDuration(asset.timeSpent) }}

          <validation-cell
            :class="{
              'validation-cell': !hiddenColumns[columnId],
              'hidden-validation-cell': hiddenColumns[columnId]
            }"
            :key="columnId + '-' + asset.id"
            :ref="'validation-' + getIndex(i, k) + '-' + j"
            :column="taskTypeMap[columnId]"
            :entity="asset"
            :task-test="taskMap[asset.validations[columnId]]"
            :selected="assetSelectionGrid[getIndex(i, k)][j]"
            :rowX="getIndex(i, k)"
            :columnY="j"
            :minimized="hiddenColumns[columnId]"
            :is-static="true"
            :is-assignees="isShowAssignations"
            @select="onTaskSelected"
            @unselect="onTaskUnselected"
            v-for="(columnId, j) in sortedValidationColumns"
            v-if="!hiddenColumns[columnId] || isShowInfos"
          />
          <row-actions v-if="isCurrentUserManager"
            :entry="asset"
            :edit-route="editPath(asset.id)"
            :delete-route="deletePath(asset.id)"
            :restore-route="restorePath(asset.id)"
          />

    {{ displayedAssetsLength }} {{ $tc('assets.number', displayedAssetsLength) }}

</template>


missing class

missing class


Move the `user` object out of the `member` object to make life easier; Fixed feedback on success and error of POST


remove reaction to same route since swap isnt reused

<template>

    <swap-confirmation
      :to="confirmInfo.to"
      :from="confirmInfo.from"
      :from-img="confirmInfo.fromImg"
      :from-type="confirmInfo.fromType"
      :to-type="confirmInfo.toType"
      :to-img="confirmInfo.toImg"
      :show="confirmInfo.show"
      :back-func="backFunction"
      :from-val="confirmInfo.fromVal"
      :to-val="confirmInfo.toVal"
      :valid-until="confirmInfo.validUntil"
      :send="executeTrade"
    />
    <v-row>
      <v-col cols="8">
        <mew6-white-sheet>
          <interface-wrap title="Swap">

                <mew-select
                  :value="fromTokenType"
                  :items="fromTokens"
                  label="From"
                  @input="setFromToken"
                />
                <mew-input
                  label="you'll send"
                  placeholder=""
                  :value="tokenInValue"
                  type="number"
                  @input="setTokenInValue"
                />

                <mew-select
                  ref="toToken"
                  :value="toTokenType"
                  :items="toTokens"
                  label="To"
                  @input="setToToken"
                />
                <mew-input
                  label="you'll receive"
                  placeholder=""
                  type="number"
                  disabled
                  :value="tokenOutValue"
                />

            <mew-address-select
              class="mt-5"
              copy-tooltip="Copy"
              save-tooltip="Save"
              :enable-save-address="true"
              label="To address"
              :items="addresses"
              placeholder="Please enter an address"
              success-toast="Success"
              :is-valid-address="false"
              :value="address"
              @input="setToAddress"
            />

= 1" class="mt-5">

Select a provider

              <v-row>
                <v-col
                  v-for="(quote, idx) in availableQuotes"
                  :key="`quote-${idx}`"
                  cols="6"
                  lg="6"
                  sm="12"
                >
                  <v-card flat color="tableHeader" class="pa-6">

                      <mew-checkbox
                        :value="quote.isSelected"
                        @input="setProvider($event, idx)"
                      />

                      1 {{ fromTokenType.symbol }} = {{ quote.rate }}
                      {{ toTokenType.symbol }}

{{ quote.exchangeInfo.name }}

                  </v-card>
                </v-col>
              </v-row>

            <mew-expand-panel
              v-show="step >= 2"
              is-toggle
              has-dividers
              :panel-items="exPannel"
              class="mt-4 mb-10 swap-expend"
            >
              <template #panelBody1>
                <mew-input
                  label="Gas Price"
                  placeholder=" "
                  right-label="Gwei"
                  :value="gasPriceGwei"
                  disabled
                />
                <mew-input
                  label="Total Gas Limit"
                  placeholder=" "
                  right-label="Wei"
                  disabled
                  :value="totalGasLimit"
                />
              </template>
            </mew-expand-panel>

= 2" class="text-center">
              <mew-button
                title="Swap"
                :has-full-width="false"
                btn-size="xlarge"
                @click.native="showConfirm()"
              />

          </interface-wrap>
        </mew6-white-sheet>
      </v-col>
      <v-spacer cols="1" />
      <v-col cols="4">
        <module-network />
      </v-col>
    </v-row>

</template>


Show no search results text

Show no search results text

Signed-off-by: Marco Ambrosini <3397c7e210a9d1588196cfebb12b2c6b133f6934@pm.me>

<template>

		<template v-if="addableUsers.length !== 0">

			<ParticipantsList
				:items="addableUsers"
				@click="handleClickParticipant" />
		</template>

		<template v-if="addableGroups.length !== 0">

			<ParticipantsList
				:items="addableGroups"
				@click="handleClickParticipant" />
		</template>

		<template v-if="addableEmails.length !== 0">

			<ParticipantsList
				:items="addableEmails"
				@click="handleClickParticipant" />
		</template>

		<template v-if="addableCircles.length !== 0">

			<ParticipantsList
				:items="addableCircles"
				@click="handleClickParticipant" />
		</template>

		<Hint v-if="contactsLoading" :hint="t('spreed', 'Searching …')" />
		<Hint v-if="!contactsLoading && sourcesWithoutResults" :hint="t('spreed', 'No search results')" />
		<template v-if="isNewGroupConversation">
			<template v-if="noResults">

					{{ t('spreed', 'No results') }}

			</template>

					{{ t('spreed', 'Search for more contacts') }}

		</template>

</template>

<template>

		<template v-if="addableUsers.length !== 0">

			<ParticipantsList
				:items="addableUsers"
				@click="handleClickParticipant" />
		</template>

		<template v-if="addableGroups.length !== 0">

			<ParticipantsList
				:items="addableGroups"
				@click="handleClickParticipant" />
		</template>

		<template v-if="addableEmails.length !== 0">

			<ParticipantsList
				:items="addableEmails"
				@click="handleClickParticipant" />
		</template>

		<template v-if="addableCircles.length !== 0">

			<ParticipantsList
				:items="addableCircles"
				@click="handleClickParticipant" />
		</template>

		<Hint v-if="contactsLoading" :hint="t('spreed', 'Searching …')" />
		<Hint v-if="!contactsLoading && !isNewGroupConversation" :hint="t('spreed', 'No search results')" />
		<template v-if="isNewGroupConversation">
			<template v-if="noResults">

					{{ t('spreed', 'No results') }}

			</template>

					{{ t('spreed', 'Search for more contacts') }}

		</template>

</template>


Pulling data from SF

Pulling data from SF

<template>

      {{ data[0].label }} new members towards goal of {{ data[1].label }}.

</template>

<template>
  <div>{{ data[0].label }} new members towards goal of {{ data[1].label }}.</div>
</template>

<script>
import axios from 'axios';

export default {
  name: 'Thermometer',

  data() {
    return {
      loading: true,
      error: false,
      data: [
        { slug: 'actual', label: '0', value: 0 },
        { slug: 'goal', label: '350', value: 0 },
      ],
    };
  },
  mounted() {
    this.getSalesforceReport();
  },
  methods: {
    getSalesforceReport() {
      const url = 'https://membership.texastribune.org/smd18-report.json';
      axios.get(url)
        .then(({
          data: {
            'T!T': report,
          },
        }) => {
          // this.data[0].label = report.aggregates[0].label;
          // this.data[0].value = report.aggregates[0].value;
          // this.data[1].label = report.aggregates[1].label;
          // this.data[1].value = report.aggregates[1].value;
          this.loading = false;
        })
        .catch(() => {
          this.error = true;
          this.loading = false;
        });
    },
  },
};
</script>


Undo docs change

Undo docs change

<template>

  <template slot-scope='{ row }'>

  </template>

</template>


Switch: compatible with vue ssr, fixed #3752 (#3820)

<template>

    <input
      class="el-switch__input"
      type="checkbox"
      @change="handleChange"
      v-model="_value"
      :name="name"
      :disabled="disabled">

    <transition name="label-fade">

        {{ onText }}

    </transition>
    <transition name="label-fade">

        {{ offText }}

    </transition>

</template>


saving date once selected to be able to access the data from btrz-date-range

<template>
  <div :class="{
      'input--focused': focused,
      'input--empty': isEmpty,
      'input--filled': !isEmpty
    }">
    <btrz-label :id="id" :label="label"></btrz-label>
    <input class="form-control calendar-bkg"
    ref="input"
    :id="id"
    :disabled="disabled"
    @input="valueUpdated($event.target.value);"
    @blur="focusUpdated('blur', $event.target.value);"
    @focus="focusUpdated('focus', $event.target.value);"/>
    <btrz-errors :errors="errors"></btrz-errors>
  </div>
</template>

<script>
  import moment from "moment";
  import BtrzLabel from "../../btrz-vue-components/src/btrz-label";
  import BtrzErrors from "../../btrz-vue-components/src/btrz-errors";

  const pickadateI18nStrings = {
    en: {
      monthsFull: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
      monthsShort: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"],
      weekdaysShort: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"],
      // Buttons
      today: "Today",
      clear: "Clear",
      close: "Close",
      // Accessibility labels
      labelMonthNext: "Next month",
      labelMonthPrev: "Previous month",
      labelMonthSelect: "Select a month",
      labelYearSelect: "Select a year",
    },
    fr: {
      monthsFull: ["Janvier", "Février", "Mars", "Avril", "Mai", "Juin", "Juillet", "Août", "Septembre", "Octobre", "Novembre", "Décembre"],
      monthsShort: ["Jan", "Fev", "Mar", "Avr", "Mai", "Juin", "Juil", "Aou", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Dimanche", "Lundi", "Mardi", "Mercredi", "Jeudi", "Vendredi", "Samedi"],
      weekdaysShort: ["Dim", "Lun", "Mar", "Mer", "Jeu", "Ven", "Sam"],
      // Buttons
      today: "Aujourd\"hui",
      clear: "Effacer",
      close: "Fermer",
      // Accessibility labels
      labelMonthNext: "Mois suivant",
      labelMonthPrev: "Mois précédent",
      labelMonthSelect: "Sélectionner un mois",
      labelYearSelect: "Sélectionner une année"
    }
  };

  export default {
    name: "BtrzDateInput",
    components: {
      BtrzLabel,
      BtrzErrors
    },
    dependencies: ["logger"],
    props: {
      id: {type: String},
      placeholder: {type: String},
      name: {type: String},
      "value": {"default": null},
      // value: Supports setting Date, [YEAR, MONTH, DAY], timestamp (int) or string matching submitFormat
      displayFormat: {type: String, "default": "dd mmmm, yyyy"}, // Pickadate format
      submitFormat: {type: String, "default": "YYYY-MM-DD"}, // Momentjs format
      minDate: {"default": false},
      lang: {type: String, required: true},
      disabled: {type: Boolean, "default": false},
      errors: {type: Object},
      label: {type: String}
    },
    model: {
      prop: "value",
      event: "change"
    },
    watch: {
      value(newValue) {
        this.setPickadateDate(newValue);
      },
      lang(newLang) {
        const translations = this.getTranslation(newLang);
        Object.assign(this.picker.component.settings, translations);
        this.picker.set("select", this.picker.get("select"), {muted: true});
        this.picker.render(true);
      },
      minDate(newMinDate) {
        this.setPickadateMinDate(newMinDate);
      }
    },
    mounted() {
      require("imports-loader?define=>false!../node_modules/pickadate/lib/picker.date");
      require("../node_modules/pickadate/lib/themes/default.css");
      require("../node_modules/pickadate/lib/themes/default.date.css");

      const baseConfig = {
        onSet: this.onSet,
        format: this.displayFormat
      };

      const translations = this.getTranslation(this.lang);
      const config = Object.assign(baseConfig, translations);
      const $input = $(this.$refs.input).pickadate(config);
      this.picker = $input.pickadate("picker");
      this.setPickadateDate(this.value);
      this.setPickadateMinDate(this.minDate);
    },
    methods: {
      formatDate(date) {
        if (this.submitFormat) {
          return date ? moment(date).format(this.submitFormat) : date;
        } else {
          return date;
        }
      },
      onSet(context) {

        if ("select" in context) {
          const date = this.formatDate(context.select);
          this.$emit("change", date);
          this.isEmpty = !Boolean(date);
          this.value = date;
        } else if ("clear" in context) {
          this.$emit("change", null);
          this.isEmpty = !Boolean(null);
          this.value = null;
        }
      },
      getTranslation(lang) {
        if (!(this.lang in pickadateI18nStrings)) {
          this.logger.warn("Could not find the specified language, defaulting to english...");
          return pickadateI18nStrings.en;
        }
        return pickadateI18nStrings[lang];
      },
      setPickadateMinDate(minDate) {
        let parsedMinDate = null;
        if (minDate) {
          parsedMinDate = this.submitFormat ? moment(minDate, this.submitFormat).toDate() : minDate;
          const selectedDate = this.picker.get("select");
          if (selectedDate) {
            if (moment(selectedDate.obj).isBefore(parsedMinDate, "days")) {
              this.setPickadateDate(null);
              this.$emit("change", null);
            }
          }
        } else {
          parsedMinDate = false;
        }
        this.picker.set("min", parsedMinDate);
      },
      setPickadateDate(newDate) {
        let date = null;

        if (typeof (newDate) === "string") {
          if (this.submitFormat) {
            date = moment(newDate, this.submitFormat);
            if (!date.isValid()) {
              throw new Error(date.toString());
            }
            date = date.toDate();
          } else {
            throw new Error("No submitFormat specified for this date");
          }
        } else if (newDate === null) {
          date = null;
        } else {
          date = moment(newDate).toDate();
        }
        this.picker.set("select", date, {muted: true});
      },
      valueUpdated(value) {
        this.inputValue = value;
      },
      focusUpdated(focus, value) {
        this.focused = !this.focused;
      }
    },
    data() {
      return {isEmpty: true, focused: false, inputValue: this.value};
    }
  };

</script>

<template>
  <div :class="{
      'input--focused': focused,
      'input--empty': isEmpty,
      'input--filled': !isEmpty
    }">
    <btrz-label :id="id" :label="label"></btrz-label>
    <input class="form-control calendar-bkg"
    ref="input"
    :id="id"
    :disabled="disabled"
    @input="valueUpdated($event.target.value);"
    @blur="focusUpdated('blur', $event.target.value);"
    @focus="focusUpdated('focus', $event.target.value);"/>
    <btrz-errors :errors="errors"></btrz-errors>
  </div>
</template>

<script>
  import moment from "moment";
  import BtrzLabel from "../../btrz-vue-components/src/btrz-label";
  import BtrzErrors from "../../btrz-vue-components/src/btrz-errors";

  const pickadateI18nStrings = {
    en: {
      monthsFull: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
      monthsShort: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"],
      weekdaysShort: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"],
      // Buttons
      today: "Today",
      clear: "Clear",
      close: "Close",
      // Accessibility labels
      labelMonthNext: "Next month",
      labelMonthPrev: "Previous month",
      labelMonthSelect: "Select a month",
      labelYearSelect: "Select a year",
    },
    fr: {
      monthsFull: ["Janvier", "Février", "Mars", "Avril", "Mai", "Juin", "Juillet", "Août", "Septembre", "Octobre", "Novembre", "Décembre"],
      monthsShort: ["Jan", "Fev", "Mar", "Avr", "Mai", "Juin", "Juil", "Aou", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Dimanche", "Lundi", "Mardi", "Mercredi", "Jeudi", "Vendredi", "Samedi"],
      weekdaysShort: ["Dim", "Lun", "Mar", "Mer", "Jeu", "Ven", "Sam"],
      // Buttons
      today: "Aujourd\"hui",
      clear: "Effacer",
      close: "Fermer",
      // Accessibility labels
      labelMonthNext: "Mois suivant",
      labelMonthPrev: "Mois précédent",
      labelMonthSelect: "Sélectionner un mois",
      labelYearSelect: "Sélectionner une année"
    }
  };

  export default {
    name: "BtrzDateInput",
    components: {
      BtrzLabel,
      BtrzErrors
    },
    dependencies: ["logger"],
    props: {
      id: {type: String},
      placeholder: {type: String},
      name: {type: String},
      "value": {"default": null},
      // value: Supports setting Date, [YEAR, MONTH, DAY], timestamp (int) or string matching submitFormat
      displayFormat: {type: String, "default": "dd mmmm, yyyy"}, // Pickadate format
      submitFormat: {type: String, "default": "YYYY-MM-DD"}, // Momentjs format
      minDate: {"default": false},
      lang: {type: String, required: true},
      disabled: {type: Boolean, "default": false},
      errors: {type: Object},
      label: {type: String}
    },
    model: {
      prop: "value",
      event: "change"
    },
    watch: {
      value(newValue) {
        this.setPickadateDate(newValue);
      },
      lang(newLang) {
        const translations = this.getTranslation(newLang);
        Object.assign(this.picker.component.settings, translations);
        this.picker.set("select", this.picker.get("select"), {muted: true});
        this.picker.render(true);
      },
      minDate(newMinDate) {
        this.setPickadateMinDate(newMinDate);
      }
    },
    mounted() {
      require("imports-loader?define=>false!../node_modules/pickadate/lib/picker.date");
      require("../node_modules/pickadate/lib/themes/default.css");
      require("../node_modules/pickadate/lib/themes/default.date.css");

      const baseConfig = {
        onSet: this.onSet,
        format: this.displayFormat
      };

      const translations = this.getTranslation(this.lang);
      const config = Object.assign(baseConfig, translations);
      const $input = $(this.$refs.input).pickadate(config);
      this.picker = $input.pickadate("picker");
      this.setPickadateDate(this.value);
      this.setPickadateMinDate(this.minDate);
    },
    methods: {
      formatDate(date) {
        if (this.submitFormat) {
          return date ? moment(date).format(this.submitFormat) : date;
        } else {
          return date;
        }
      },
      onSet(context) {

        if ("select" in context) {
          const date = this.formatDate(context.select);
          this.$emit("change", date);
          this.isEmpty = !Boolean(date);
        } else if ("clear" in context) {
          this.$emit("change", null);
          this.isEmpty = !Boolean(null);
        }
      },
      getTranslation(lang) {
        if (!(this.lang in pickadateI18nStrings)) {
          this.logger.warn("Could not find the specified language, defaulting to english...");
          return pickadateI18nStrings.en;
        }
        return pickadateI18nStrings[lang];
      },
      setPickadateMinDate(minDate) {
        let parsedMinDate = null;
        if (minDate) {
          parsedMinDate = this.submitFormat ? moment(minDate, this.submitFormat).toDate() : minDate;
          const selectedDate = this.picker.get("select");
          if (selectedDate) {
            if (moment(selectedDate.obj).isBefore(parsedMinDate, "days")) {
              this.setPickadateDate(null);
              this.$emit("change", null);
            }
          }
        } else {
          parsedMinDate = false;
        }
        this.picker.set("min", parsedMinDate);
      },
      setPickadateDate(newDate) {
        let date = null;

        if (typeof (newDate) === "string") {
          if (this.submitFormat) {
            date = moment(newDate, this.submitFormat);
            if (!date.isValid()) {
              throw new Error(date.toString());
            }
            date = date.toDate();
          } else {
            throw new Error("No submitFormat specified for this date");
          }
        } else if (newDate === null) {
          date = null;
        } else {
          date = moment(newDate).toDate();
        }
        this.picker.set("select", date, {muted: true});
      },
      valueUpdated(value) {
        this.inputValue = value;
      },
      focusUpdated(focus, value) {
        this.focused = !this.focused;
      }
    },
    data() {
      return {isEmpty: true, focused: false, inputValue: this.value};
    }
  };

</script>


#413: added max date in btrz-date-input.

<template>
  <div :class="{
      'input--focused': focused,
      'input--empty': isEmpty,
      'input--filled': !isEmpty
    }">
    <btrz-label :id="id" :label="label"></btrz-label>
    <input class="form-control calendar-bkg"
    ref="input"
    :id="id"
    :name="name"
    :disabled="disabled"
    @input="valueUpdated($event.target.value);"
    @blur="focusUpdated('blur', $event.target.value);"
    @focus="focusUpdated('focus', $event.target.value);"/>
    <btrz-errors :errors="errors"></btrz-errors>
  </div>
</template>

<script>
  import moment from "moment";
  import BtrzLabel from "../../btrz-vue-components/src/btrz-label";
  import BtrzErrors from "../../btrz-vue-components/src/btrz-errors";

  const pickadateI18nStrings = {
    en: {
      monthsFull: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
      monthsShort: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"],
      weekdaysShort: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"],
      // Buttons
      today: "Today",
      clear: "Clear",
      close: "Close",
      // Accessibility labels
      labelMonthNext: "Next month",
      labelMonthPrev: "Previous month",
      labelMonthSelect: "Select a month",
      labelYearSelect: "Select a year",
    },
    fr: {
      monthsFull: ["Janvier", "Février", "Mars", "Avril", "Mai", "Juin", "Juillet", "Août", "Septembre", "Octobre", "Novembre", "Décembre"],
      monthsShort: ["Jan", "Fev", "Mar", "Avr", "Mai", "Juin", "Juil", "Aou", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Dimanche", "Lundi", "Mardi", "Mercredi", "Jeudi", "Vendredi", "Samedi"],
      weekdaysShort: ["Dim", "Lun", "Mar", "Mer", "Jeu", "Ven", "Sam"],
      // Buttons
      today: "Aujourd\"hui",
      clear: "Effacer",
      close: "Fermer",
      // Accessibility labels
      labelMonthNext: "Mois suivant",
      labelMonthPrev: "Mois précédent",
      labelMonthSelect: "Sélectionner un mois",
      labelYearSelect: "Sélectionner une année"
    },
    de: {
      monthsFull: ["August", "April", "Mai", "April", "Mai", "April", "Mai", "April", "Mai", "August"],
      monthsShort: ["Jan", "Fev", "Mar", "Avr", "Mai", "Juin", "Juil", "Aou", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Sonntag", "Montag", "Dienstag", "Mittwoch", "Donnerstag", "Freitag", "Samstag"],
      weekdaysShort: ["Dim", "Lun", "Mar", "Mer", "Jeu", "Ven", "Sam"],
      // Buttons
      today: "Heute",
      clear: "Klar",
      close: "Schließen",
      // Accessibility labels
      labelMonthNext: "Nächsten Monat",
      labelMonthPrev: "Vorheriger Monat",
      labelMonthSelect: "Wähle einen Monat",
      labelYearSelect: "Wählen Sie ein Jahr aus"
    },
    nl: {
      monthsFull: ["Januari", "februari", "maart", "april", "mei", "juni", "juli", "augustus", "september", "oktober", "november", "december"],
      monthsShort: ["Jan", "Fev", "Mar", "Avr", "Mai", "Juin", "Juil", "Aou", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Zondag", "maandag", "dinsdag", "woensdag", "donderdag", "vrijdag", "zaterdag"],
      weekdaysShort: ["Dim", "Lun", "Mar", "Mer", "Jeu", "Ven", "Sam"],
      // Buttons
      today: "Vandaag",
      clear: "Duidelijk",
      close: "Dichtbij",
      // Accessibility labels
      labelMonthNext: "Mois suivant",
      labelMonthPrev: "Mois précédent",
      labelMonthSelect: "Sélectionner un mois",
      labelYearSelect: "Sélectionner une année"
    }
  };

  export default {
    name: "BtrzDateInput",
    components: {
      BtrzLabel,
      BtrzErrors
    },
    dependencies: ["logger"],
    props: {
      id: {type: String},
      placeholder: {type: String},
      name: {type: String},
      "value": {"default": null},
      // value: Supports setting Date, [YEAR, MONTH, DAY], timestamp (int) or string matching submitFormat
      displayFormat: {type: String, "default": "dd mmmm, yyyy"}, // Pickadate format
      submitFormat: {type: String, "default": "YYYY-MM-DD"}, // Momentjs format
      minDate: {"default": false},
      maxDate: {"default": false},
      lang: {type: String, required: true},
      disabled: {type: Boolean, "default": false},
      errors: {type: Object},
      label: {type: String}
    },
    model: {
      prop: "value",
      event: "change"
    },
    watch: {
      value(newValue) {
        this.setPickadateDate(newValue);
      },
      lang(newLang) {
        const translations = this.getTranslation(newLang);
        Object.assign(this.picker.component.settings, translations);
        this.picker.set("select", this.picker.get("select"), {muted: true});
        this.picker.render(true);
      },
      minDate(newMinDate) {
        this.setPickadateLimit(newMinDate, "min");
      },
      maxDate(newMaxDate) {
        this.setPickadateLimit(newMaxDate, "max");
      }
    },
    mounted() {
      require("imports-loader?define=>false!pickadate/lib/picker.date");
      require("pickadate/lib/themes/default.css");
      require("pickadate/lib/themes/default.date.css");

      const baseConfig = {
        onSet: this.onSet,
        format: this.displayFormat
      };

      const translations = this.getTranslation(this.lang);
      const config = Object.assign(baseConfig, translations);
      const $input = $(this.$refs.input).pickadate(config);
      this.picker = $input.pickadate("picker");
      this.setPickadateDate(this.value);
      this.setPickadateLimit(this.minDate, "min");
      this.setPickadateLimit(this.maxDate, "max");
    },
    methods: {
      formatDate(date) {
        if (this.submitFormat) {
          return date ? moment(date).format(this.submitFormat) : date;
        } else {
          return date;
        }
      },
      onSet(context) {

        if ("select" in context) {
          const date = this.formatDate(context.select);
          this.$emit("change", date);
          this.isEmpty = !Boolean(date);
        } else if ("clear" in context) {
          this.$emit("change", null);
          this.isEmpty = !Boolean(null);
        }
      },
      getTranslation(lang) {
        if (!(this.lang in pickadateI18nStrings)) {
          this.logger.warn(`Could not find the ${this.lang} language, defaulting to english...`);
          return pickadateI18nStrings.en;
        }
        return pickadateI18nStrings[lang];
      },
      setPickadateLimit(date, limit){
        let parsedDate = null;
        if (date) {
          parsedDate = this.submitFormat ? moment(date, this.submitFormat).toDate() : date;
          const selectedDate = this.picker.get("select");
          if (selectedDate) {
            if (moment(selectedDate.obj).isBefore(parsedDate, "days")) {
              this.setPickadateDate(null);
              this.$emit("change", null);
            }
          }
        } else {
          parsedDate = false;
        }
        this.picker.set(limit, parsedDate);
      },
      setPickadateDate(newDate) {
        let date = null;

        if (typeof (newDate) === "string") {
          if (this.submitFormat) {
            date = moment(newDate, this.submitFormat);
            if (!date.isValid()) {
              throw new Error(date.toString());
            }
            date = date.toDate();
          } else {
            throw new Error("No submitFormat specified for this date");
          }
        } else if (newDate === null) {
          date = null;
        } else {
          date = moment(newDate).toDate();
        }
        this.picker.set("select", date, {muted: true});
      },
      valueUpdated(value) {
        this.inputValue = value;
      },
      focusUpdated(focus, value) {
        this.focused = !this.focused;
      }
    },
    data() {
      return {isEmpty: true, focused: false, inputValue: this.value};
    }
  };

</script>

<template>
  <div :class="{
      'input--focused': focused,
      'input--empty': isEmpty,
      'input--filled': !isEmpty
    }">
    <btrz-label :id="id" :label="label"></btrz-label>
    <input class="form-control calendar-bkg"
    ref="input"
    :id="id"
    :name="name"
    :disabled="disabled"
    @input="valueUpdated($event.target.value);"
    @blur="focusUpdated('blur', $event.target.value);"
    @focus="focusUpdated('focus', $event.target.value);"/>
    <btrz-errors :errors="errors"></btrz-errors>
  </div>
</template>

<script>
  import moment from "moment";
  import BtrzLabel from "../../btrz-vue-components/src/btrz-label";
  import BtrzErrors from "../../btrz-vue-components/src/btrz-errors";

  const pickadateI18nStrings = {
    en: {
      monthsFull: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
      monthsShort: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"],
      weekdaysShort: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"],
      // Buttons
      today: "Today",
      clear: "Clear",
      close: "Close",
      // Accessibility labels
      labelMonthNext: "Next month",
      labelMonthPrev: "Previous month",
      labelMonthSelect: "Select a month",
      labelYearSelect: "Select a year",
    },
    fr: {
      monthsFull: ["Janvier", "Février", "Mars", "Avril", "Mai", "Juin", "Juillet", "Août", "Septembre", "Octobre", "Novembre", "Décembre"],
      monthsShort: ["Jan", "Fev", "Mar", "Avr", "Mai", "Juin", "Juil", "Aou", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Dimanche", "Lundi", "Mardi", "Mercredi", "Jeudi", "Vendredi", "Samedi"],
      weekdaysShort: ["Dim", "Lun", "Mar", "Mer", "Jeu", "Ven", "Sam"],
      // Buttons
      today: "Aujourd\"hui",
      clear: "Effacer",
      close: "Fermer",
      // Accessibility labels
      labelMonthNext: "Mois suivant",
      labelMonthPrev: "Mois précédent",
      labelMonthSelect: "Sélectionner un mois",
      labelYearSelect: "Sélectionner une année"
    },
    de: {
      monthsFull: ["August", "April", "Mai", "April", "Mai", "April", "Mai", "April", "Mai", "August"],
      monthsShort: ["Jan", "Fev", "Mar", "Avr", "Mai", "Juin", "Juil", "Aou", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Sonntag", "Montag", "Dienstag", "Mittwoch", "Donnerstag", "Freitag", "Samstag"],
      weekdaysShort: ["Dim", "Lun", "Mar", "Mer", "Jeu", "Ven", "Sam"],
      // Buttons
      today: "Heute",
      clear: "Klar",
      close: "Schließen",
      // Accessibility labels
      labelMonthNext: "Nächsten Monat",
      labelMonthPrev: "Vorheriger Monat",
      labelMonthSelect: "Wähle einen Monat",
      labelYearSelect: "Wählen Sie ein Jahr aus"
    },
    nl: {
      monthsFull: ["Januari", "februari", "maart", "april", "mei", "juni", "juli", "augustus", "september", "oktober", "november", "december"],
      monthsShort: ["Jan", "Fev", "Mar", "Avr", "Mai", "Juin", "Juil", "Aou", "Sep", "Oct", "Nov", "Dec"],
      weekdaysFull: ["Zondag", "maandag", "dinsdag", "woensdag", "donderdag", "vrijdag", "zaterdag"],
      weekdaysShort: ["Dim", "Lun", "Mar", "Mer", "Jeu", "Ven", "Sam"],
      // Buttons
      today: "Vandaag",
      clear: "Duidelijk",
      close: "Dichtbij",
      // Accessibility labels
      labelMonthNext: "Mois suivant",
      labelMonthPrev: "Mois précédent",
      labelMonthSelect: "Sélectionner un mois",
      labelYearSelect: "Sélectionner une année"
    }
  };

  export default {
    name: "BtrzDateInput",
    components: {
      BtrzLabel,
      BtrzErrors
    },
    dependencies: ["logger"],
    props: {
      id: {type: String},
      placeholder: {type: String},
      name: {type: String},
      "value": {"default": null},
      // value: Supports setting Date, [YEAR, MONTH, DAY], timestamp (int) or string matching submitFormat
      displayFormat: {type: String, "default": "dd mmmm, yyyy"}, // Pickadate format
      submitFormat: {type: String, "default": "YYYY-MM-DD"}, // Momentjs format
      minDate: {"default": false},
      lang: {type: String, required: true},
      disabled: {type: Boolean, "default": false},
      errors: {type: Object},
      label: {type: String}
    },
    model: {
      prop: "value",
      event: "change"
    },
    watch: {
      value(newValue) {
        this.setPickadateDate(newValue);
      },
      lang(newLang) {
        const translations = this.getTranslation(newLang);
        Object.assign(this.picker.component.settings, translations);
        this.picker.set("select", this.picker.get("select"), {muted: true});
        this.picker.render(true);
      },
      minDate(newMinDate) {
        this.setPickadateMinDate(newMinDate);
      }
    },
    mounted() {
      require("imports-loader?define=>false!pickadate/lib/picker.date");
      require("pickadate/lib/themes/default.css");
      require("pickadate/lib/themes/default.date.css");

      const baseConfig = {
        onSet: this.onSet,
        format: this.displayFormat
      };

      const translations = this.getTranslation(this.lang);
      const config = Object.assign(baseConfig, translations);
      const $input = $(this.$refs.input).pickadate(config);
      this.picker = $input.pickadate("picker");
      this.setPickadateDate(this.value);
      this.setPickadateMinDate(this.minDate);
    },
    methods: {
      formatDate(date) {
        if (this.submitFormat) {
          return date ? moment(date).format(this.submitFormat) : date;
        } else {
          return date;
        }
      },
      onSet(context) {

        if ("select" in context) {
          const date = this.formatDate(context.select);
          this.$emit("change", date);
          this.isEmpty = !Boolean(date);
        } else if ("clear" in context) {
          this.$emit("change", null);
          this.isEmpty = !Boolean(null);
        }
      },
      getTranslation(lang) {
        if (!(this.lang in pickadateI18nStrings)) {
          this.logger.warn(`Could not find the ${this.lang} language, defaulting to english...`);
          return pickadateI18nStrings.en;
        }
        return pickadateI18nStrings[lang];
      },
      setPickadateMinDate(minDate) {
        let parsedMinDate = null;
        if (minDate) {
          parsedMinDate = this.submitFormat ? moment(minDate, this.submitFormat).toDate() : minDate;
          const selectedDate = this.picker.get("select");
          if (selectedDate) {
            if (moment(selectedDate.obj).isBefore(parsedMinDate, "days")) {
              this.setPickadateDate(null);
              this.$emit("change", null);
            }
          }
        } else {
          parsedMinDate = false;
        }
        this.picker.set("min", parsedMinDate);
      },
      setPickadateDate(newDate) {
        let date = null;

        if (typeof (newDate) === "string") {
          if (this.submitFormat) {
            date = moment(newDate, this.submitFormat);
            if (!date.isValid()) {
              throw new Error(date.toString());
            }
            date = date.toDate();
          } else {
            throw new Error("No submitFormat specified for this date");
          }
        } else if (newDate === null) {
          date = null;
        } else {
          date = moment(newDate).toDate();
        }
        this.picker.set("select", date, {muted: true});
      },
      valueUpdated(value) {
        this.inputValue = value;
      },
      focusUpdated(focus, value) {
        this.focused = !this.focused;
      }
    },
    data() {
      return {isEmpty: true, focused: false, inputValue: this.value};
    }
  };

</script>


更新App的标题

更新App的标题

<template>
  <div id="app">
    <EgdHeader :headTitle="title" :goBack="goBack"></EgdHeader>
    <transition name="router-fade" mode="out-in">
      <router-view class="view"></router-view>
    </transition>
  </div>
</template>

<script>
  import EgdHeader from 'header'
  import EgdFooter from 'footer'
  export default {
    data(){
      return {
        title : '重大事项决策管理平台(测试)',
        goBack : false,
        showFooter : true
      }
    },
    components: {
      EgdHeader,
      EgdFooter
    },
    mounted(){
      this.$on("change-header", (...params) => {
        [this.title, this.goBack] = params
      })
    }
  }
</script>

<style lang="scss">
  @import './assets/css/common';
  .router-fade-enter-active, .router-fade-leave-active {
    transition: opacity .3s;
  }
  .router-fade-enter, .router-fade-leave-active {
    opacity: 0;
  }
  .view {
    position: relative;
    padding-top: 2.5rem;
    background-color: #fff;
    height: 100%;
    width: 100%;
  }
</style>

<template>
  <div id="app">
    <EgdHeader :headTitle="title" :goBack="goBack"></EgdHeader>
    <transition name="router-fade" mode="out-in">
      <router-view class="view"></router-view>
    </transition>
  </div>
</template>

<script>
  import EgdHeader from 'header'
  import EgdFooter from 'footer'
  export default {
    data(){
      return {
        title : '重大事项决策管理平台',
        goBack : false,
        showFooter : true
      }
    },
    components: {
      EgdHeader,
      EgdFooter
    },
    mounted(){
      this.$on("change-header", (...params) => {
        [this.title, this.goBack] = params
      })
    }
  }
</script>

<style lang="scss">
  @import './assets/css/common';
  .router-fade-enter-active, .router-fade-leave-active {
    transition: opacity .3s;
  }
  .router-fade-enter, .router-fade-leave-active {
    opacity: 0;
  }
  .view {
    position: relative;
    padding-top: 2.5rem;
    background-color: #fff;
    height: 100%;
    width: 100%;
  }
</style>


添加背景色

添加背景色

<template>
  <div id="app">
    <br-header></br-header>
    <router-view></router-view>
    <br-footer></br-footer>
  </div>
</template>

<style>
  #app {
  /*background: #58a;*/
    height: 100vh;
    /*background: linear-gradient(-45deg, transparent 185px, #58a 0),*/
    /*linear-gradient(45deg, transparent 15px, #655 0);*/
    background: repeating-linear-gradient(-45deg, #acadad, #acadad 20%, #959696 0, #959696 80%);}
</style>

<script>
  import BrHeader from './components/Header.vue'
  import BrFooter from './components/Footer'

  export default {
    name: 'app',
    components: {
      BrHeader,
      BrFooter
    }
  }
</script>

<style>
  html, body, div, span, applet, object, iframe,
h1, h2, h3, h4, h5, h6, p, blockquote, pre,
a, abbr, acronym, address, big, cite, code,
del, dfn, em, img, ins, kbd, q, s, samp,
small, strike, strong, sub, sup, tt, var,
b, u, i, center,
dl, dt, dd, ol, ul, li,
fieldset, form, label, legend,
table, caption, tbody, tfoot, thead, tr, th, td,
article, aside, canvas, details, embed,
figure, figcaption, footer, header, hgroup,
menu, nav, output, ruby, section, summary,
time, mark, audio, video {
	margin: 0;
	padding: 0;
	border: 0;
	font-size: 100%;
	font: inherit;
	vertical-align: baseline;
}
/* HTML5 display-role reset for older browsers */
article, aside, details, figcaption, figure,
footer, header, hgroup, menu, nav, section {
	display: block;
}
body {
	line-height: 1;
}
ol, ul {
	list-style: none;
}
blockquote, q {
	quotes: none;
}
blockquote:before, blockquote:after,
q:before, q:after {
	content: '';
	content: none;
}
table {
	border-collapse: collapse;
	border-spacing: 0;
}

.clearfix:before,
.clearfix:after {
  display: table;
  content: " ";
}
.clearfix:after {
  clear: both;
}

</style>

<template>
  <div id="app">
    <br-header></br-header>
    <router-view></router-view>
    <br-footer></br-footer>
  </div>
</template>

<script>
  import BrHeader from './components/Header.vue'
  import BrFooter from './components/Footer'

  export default {
    name: 'app',
    components: {
      BrHeader,
      BrFooter
    }
  }
</script>

<style>
  html, body, div, span, applet, object, iframe,
h1, h2, h3, h4, h5, h6, p, blockquote, pre,
a, abbr, acronym, address, big, cite, code,
del, dfn, em, img, ins, kbd, q, s, samp,
small, strike, strong, sub, sup, tt, var,
b, u, i, center,
dl, dt, dd, ol, ul, li,
fieldset, form, label, legend,
table, caption, tbody, tfoot, thead, tr, th, td,
article, aside, canvas, details, embed,
figure, figcaption, footer, header, hgroup,
menu, nav, output, ruby, section, summary,
time, mark, audio, video {
	margin: 0;
	padding: 0;
	border: 0;
	font-size: 100%;
	font: inherit;
	vertical-align: baseline;
}
/* HTML5 display-role reset for older browsers */
article, aside, details, figcaption, figure,
footer, header, hgroup, menu, nav, section {
	display: block;
}
body {
	line-height: 1;
}
ol, ul {
	list-style: none;
}
blockquote, q {
	quotes: none;
}
blockquote:before, blockquote:after,
q:before, q:after {
	content: '';
	content: none;
}
table {
	border-collapse: collapse;
	border-spacing: 0;
}

.clearfix:before,
.clearfix:after {
  display: table;
  content: " ";
}
.clearfix:after {
  clear: both;
}

</style>


Add keep-alive

Add keep-alive

<template>

    <v-header v-bind:data="restaurant"></v-header>

        <router-link to="/goods">商品</router-link>

        <router-link to="/ratings">评价</router-link>

        <router-link to="/seller">商家</router-link>

    <keep-alive>
      <router-view :data="restaurant"></router-view>
    </keep-alive>

</template>

<template>

    <v-header v-bind:data="restaurant"></v-header>

        <router-link to="/goods">商品</router-link>

        <router-link to="/ratings">评价</router-link>

        <router-link to="/seller">商家</router-link>

    <router-view :data="restaurant"></router-view>

</template>


Size and spacing tweaks.

Size and spacing tweaks.

<template>

          Pleased to meet you!

        The Steele Family

        Joshua, Kelsie, Abigail, Rebekah, Hosanna, Kathryn, David, and
        <nuxt-link to="/blog/2019-10-14-meet-mia">
          Mia (not pictured)
        </nuxt-link>

      <DynamicMarkdown
        :render-fn="renderFn"
        :static-render-fns="staticRenderFns"
      />

</template>


Select language and topic translated. Show label always.

<template>
    <v-card id="create-question-container">
        <v-card-text>
            <v-form v-model="valid">
                <v-layout row wrap>
                    <v-flex xs12>
                        <v-text-field type="text" v-model="newQuestion" name="question"
                                      :label="$t('pages:feeds.question.yourQuestion')"
                                      :rules="[ruleFieldRequired($t('validation:fieldRequired')),
                                               ruleToManyChars($t('validation:toManyChars'), 80)]"
                                      :counter="80">
                        </v-text-field>
                    </v-flex>
                    <v-flex xs12>
                        <v-text-field type="text" v-model="description" name="description" multi-line auto-grow rows="1"
                                      :label="$t('common:description')"
                                      :rules="[ruleToManyChars($t('validation:toManyChars'), 700)]"
                                      :counter="700">
                        </v-text-field>
                    </v-flex>
                    <v-flex xs12 md5>
                        <v-select v-model="selectTopic"
                                  :label="$t('pages:feeds.question.selectTopic')"
                                  :rules="[ruleSelectMultipleRequired($t('validation:fieldRequired'))]"
                                  multiple required
                                  :items="getTopics()">
                        </v-select>
                    </v-flex>
                    <v-flex xs12 md5 offset-md2>
                        <v-select v-model="selectLang" id="select-language"
                                  :label="$t('pages:feeds.question.selectLanguage')"
                                  :rules="[ruleSelectRequired($t('validation:fieldRequired'))]"
                                  :items="getLanguages()"
                                  single-line bottom required>
                        </v-select>
                    </v-flex>
                </v-layout>
            </v-form>
        </v-card-text>
        <v-divider></v-divider>
        <v-card-actions>
            <v-spacer></v-spacer>
            <v-btn color="primary" flat :disabled="loading"
                   @click.native="$emit('close-dialog')">{{$t("common:button.close")}}
            </v-btn>
            <v-btn color="primary" flat @click.native="createNewQuestion"
                   :disabled="!valid || loading">
                {{$t("common:button.create")}}
            </v-btn>
        </v-card-actions>
    </v-card>
</template>

<script>
    import validationRules from '~/mixins/validationRules.js';
    import topic from '~/mixins/topics.js';
    import languages from '~/mixins/languages.js';

    export default {
        props: ['question'],
        data: function () {
            return {
                newQuestion: this.question, description: '', valid: false, selectTopic: [],
                selectLang: this.$store.state.i18n.language, loading: false
            };
        },
        mixins: [validationRules, topic, languages],
        methods: {
            createNewQuestion: async function () {
                try {
                    this.loading = true;
                    let response = await this.$axios.$post('/user/question', {
                        question: this.newQuestion,
                        description: this.description,
                        topic: this.selectTopic,
                        lang: this.selectLang
                    });
                    this.loading = false;
                    this.$emit('close-dialog');
                    this.$router.push({
                        name: 'question-questionId-slug',
                        params: {questionId: response.questionId, slug: response.slug}
                    });
                } catch (error) {
                    this.loading = false;
                }
            }
        }
    }
</script>

<style lang="scss">
    #create-question-container {
        #select-language {
            label {
                display: inline-block;
                max-width: 100%;
            }
        }
    }
</style>

<template>
    <v-card id="create-question-container">
        <v-card-text>
            <v-form v-model="valid">
                <v-layout row wrap>
                    <v-flex xs12>
                        <v-text-field type="text" v-model="newQuestion" name="question"
                                      :label="$t('pages:feeds.question.yourQuestion')"
                                      :rules="[ruleFieldRequired($t('validation:fieldRequired')),
                                               ruleToManyChars($t('validation:toManyChars'), 80)]"
                                      :counter="80">
                        </v-text-field>
                    </v-flex>
                    <v-flex xs12>
                        <v-text-field type="text" v-model="description" name="description" multi-line auto-grow rows="1"
                                      :label="$t('common:description')"
                                      :rules="[ruleToManyChars($t('validation:toManyChars'), 700)]"
                                      :counter="700">
                        </v-text-field>
                    </v-flex>
                    <v-flex xs12 md5>
                        <v-select v-model="selectTopic"
                                  label="Select Topic"
                                  :rules="[ruleSelectMultipleRequired($t('validation:fieldRequired'))]"
                                  multiple required
                                  :items="getTopics()">
                        </v-select>
                    </v-flex>
                    <v-flex xs12 md5 offset-md2>
                        <v-select v-model="selectLang"
                                  label="Select Language"
                                  hint="Language of the question " persistent-hint
                                  :rules="[ruleSelectRequired($t('validation:fieldRequired'))]"
                                  :items="getLanguages()"
                                  single-line bottom required>
                        </v-select>
                    </v-flex>
                </v-layout>
            </v-form>
        </v-card-text>
        <v-divider></v-divider>
        <v-card-actions>
            <v-spacer></v-spacer>
            <v-btn color="primary" flat :disabled="loading"
                   @click.native="$emit('close-dialog')">{{$t("common:button.close")}}
            </v-btn>
            <v-btn color="primary" flat @click.native="createNewQuestion"
                   :disabled="!valid || loading">
                {{$t("common:button.create")}}
            </v-btn>
        </v-card-actions>
    </v-card>
</template>

<script>
    import validationRules from '~/mixins/validationRules.js';
    import topic from '~/mixins/topics.js';
    import languages from '~/mixins/languages.js';

    export default {
        props: ['question'],
        data: function () {
            return {
                newQuestion: this.question, description: '', valid: false, selectTopic: [],
                selectLang: this.$store.state.i18n.language, loading: false
            };
        },
        mixins: [validationRules, topic, languages],
        methods: {
            createNewQuestion: async function () {
                try {
                    this.loading = true;
                    let response = await this.$axios.$post('/user/question', {
                        question: this.newQuestion,
                        description: this.description,
                        topic: this.selectTopic,
                        lang: this.selectLang
                    });
                    this.loading = false;
                    this.$emit('close-dialog');
                    this.$router.push({
                        name: 'question-questionId-slug',
                        params: {questionId: response.questionId, slug: response.slug}
                    });
                } catch (error) {
                    this.loading = false;
                }
            }
        }
    }
</script>

<style lang="scss">
    #ask-question-container {
        padding-top: 6px;
        padding-left: 12px;
        padding-right: 12px;
        .dialog-login-info {
            margin: 24px 0;
            font-size: 14px;
            color: $secondary-text;
            border-radius: 4px;
            border: 1px solid #e0e0e0;
            padding: 8px;
        }
    }
</style>


Feature: Add predefined size for image to make waterfall resize faster

<template>

          <template v-for="item in blocks">

{{ item.description }}

                      pined by

                          <router-link
                            :to="{ name: 'user', params: {user: item.author} }">
                            {{ item.author }}
                          </router-link>

                        <template v-if="item.tags.length > 0">
                           in
                          <template v-for="tag in item.tags">

                              <router-link :to="{ name: 'tag', params: {tag: tag} }" params="{tag: tag}">{{ tag }}</router-link>

                          </template>
                        </template>

          </template>

      <loadingSpinner v-bind:show="status.loading"></loadingSpinner>
      <noMore v-bind:show="!status.hasNext"></noMore>

</template>


Fix device checker on shorter screens

Fix device checker on shorter screens

Signed-off-by: marco <3397c7e210a9d1588196cfebb12b2c6b133f6934@pm.me>

<template>
	<Modal v-if="modal"
		class="talk-modal"
		size="large"
		@close="closeModal">

				{{ t('spreed', 'Camera and microphone check') }}

				<video v-show="showVideo"
					ref="video"
					class="preview__video"
					disable-picture-in-picture="true"
					tabindex="-1" />

					<VideoBackground
						:display-name="displayName"
						:user="userId" />
					<Avatar v-if="userId"
						:size="128"
						:disable-menu="true"
						:disable-tooltip="true"
						:show-user-status="false"
						:user="userId"
						:display-name="displayName" />

						{{ firstLetterOfGuestName }}

				<button
					v-tooltip="audioButtonTooltip"
					class="device-toggle"
					:aria-label="audioButtonTooltip"
					:disabled="!audioPreviewAvailable"
					@click="toggleAudio">

						<Microphone
							v-if="audioOn"
							title=""
							decorative
							:size="20" />
						<MicrophoneOff
							v-else
							title=""
							decorative
							:size="20" />

				</button>
				<VolumeIndicator
					class="indicator"
					:audio-preview-available="audioPreviewAvailable"
					:current-volume="currentVolume"
					:volume-threshold="volumeThreshold"
					:disabled="!audioOn" />

				<button
					v-tooltip="videoButtonTooltip"
					class="device-toggle"
					:aria-label="videoButtonTooltip"
					:disabled="!videoPreviewAvailable"
					@click="toggleVideo">

						<Video
							v-if="videoOn"
							title=""
							decorative
							:size="20" />
						<VideoOff
							v-else
							title=""
							decorative
							:size="20" />

				</button>

				<button
					v-if="videoPreviewAvailable && blurPreviewAvailable"
					v-tooltip="blurButtonTooltip"
					class="device-toggle"
					:aria-label="blurButtonTooltip"
					:disabled="!blurPreviewAvailable"
					@click="toggleBlur">

						<Blur
							v-if="blurOn"
							slot="icon"
							:size="20"
							decorative
							title="" />
						<BlurOff
							v-else
							slot="icon"
							:size="20"
							decorative
							title="" />

				</button>

				<button v-if="!showDeviceSelection"
					class="select-devices"
					@click="showDeviceSelection = true">

						<Cog
							title=""
							decorative
							:size="20" />

					 {{ t('spreed', 'Choose devices') }}
				</button>
				<template v-if="showDeviceSelection">
					<MediaDevicesSelector kind="audioinput"
						:devices="devices"
						:device-id="audioInputId"
						@update:deviceId="audioInputId = $event" />
					<MediaDevicesSelector kind="videoinput"
						:devices="devices"
						:device-id="videoInputId"
						@update:deviceId="videoInputId = $event" />
				</template>

			<CheckboxRadioSwitch :checked.sync="showDeviceChecker"
				class="checkbox">
				{{ t('spreed', 'Always show this dialog before joining a call in this conversation.') }}
			</CheckboxRadioSwitch>

			<CallButton
				class="call-button"
				:force-join-call="true" />

	</Modal>
</template>


fix(form-checkbox): apply form state class to hidden inputs

<template>

            <input type="checkbox"
                   :id="safeId()"
                   v-model="computedLocalChecked"
                   :class="['form-check-input', get_StateClass]"
                   :name="get_Name"
                   :value="value"
                   :true-value="value"
                   :false-value="uncheckedValue"
                   :disabled="is_Disabled"
                   :required="is_Required"
                   ref="check"
                   autocomplete="off"
                   :aria-required="is_Required ? 'true' : null"
                   @change="handleChange">
            <slot></slot>

        <input type="checkbox"
               :id="safeId()"
               v-model="computedLocalChecked"
               :class="[is_ButtonMode ? '' : 'custom-control-input', get_StateClass]"
               :name="get_Name"
               :value="value"
               :true-value="value"
               :false-value="uncheckedValue"
               :disabled="is_Disabled"
               :required="is_Required"
               ref="check"
               autocomplete="off"
               :aria-required="is_Required ? 'true' : null"
               @focus="handleFocus"
               @blur="handleFocus"
               @change="handleChange">

            <slot></slot>

</template>

<template>

            <input type="checkbox"
                   :id="safeId()"
                   v-model="computedLocalChecked"
                   class="form-check-input"
                   :name="get_Name"
                   :value="value"
                   :true-value="value"
                   :false-value="uncheckedValue"
                   :disabled="is_Disabled"
                   :required="is_Required"
                   ref="check"
                   autocomplete="off"
                   :aria-required="is_Required ? 'true' : null"
                   @change="handleChange">
            <slot></slot>

        <input type="checkbox"
               :id="safeId()"
               v-model="computedLocalChecked"
               :class="is_ButtonMode ? '' : 'custom-control-input'"
               :name="get_Name"
               :value="value"
               :true-value="value"
               :false-value="uncheckedValue"
               :disabled="is_Disabled"
               :required="is_Required"
               ref="check"
               autocomplete="off"
               :aria-required="is_Required ? 'true' : null"
               @focus="handleFocus"
               @blur="handleFocus"
               @change="handleChange">

            <slot></slot>

</template>


Add comment

Add comment

<template>

  <v-sheet
    class="pa-12 text-center"
    rounded
    color="white"
    elevation="1"
    width="500"
  >
    <v-row
      v-for="(detail, idx) in details"
      :key="idx"
      class="d-flex align-center"
    >
      <v-col class="d-flex align-center" cols="6"
        >{{ detail.title }}
        <mew-tooltip v-if="detail.tooltip" class="ml-1" :text="detail.tooltip"
      /></v-col>
      <v-col class="font-weight-bold d-flex align-center justify-end" cols="6">

        <v-icon v-if="detail.indicator" :class="detail.class">{{
          detail.indicator
        }}</v-icon>
        {{ detail.value }}
      </v-col>
    </v-row>
    <mew-button class="mt-10" title="Confirm" btn-size="xlarge" />
  </v-sheet>
</template>


Updated status bar.

Updated status bar.

<template>

        ZenUML
        (selection)

        {{stat.value}} {{stat.name}}

      Ln {{line}}, Col {{column}}

</template>

<template>

        Markdown
        (selection)

        {{stat.value}} {{stat.name}}

      Ln {{line}}, Col {{column}}

        HTML
        (selection)

        {{stat.value}} {{stat.name}}

</template>


fix: Fixes emitted names. Closes #152.

fix: Fixes emitted names. Closes #152.

<template>

    <slot name="toolbar"></slot>

    <input
      v-if="useCustomImageHandler"
      id="file-upload"
      ref="fileInput"
      type="file"
      accept="image/*"
      style="display:none;"
      @change="emitImageInfo($event)"
    />

</template>


Material preloader

Material preloader


[Tabs] Badge color not working inside active Tab title (fix #276)

<template>

      <template v-for="(tab, index) in groupedTabs">
        <dropdown v-if="tab.tabs" role="presentation" tag="li" :class="getTabClasses(tab)">
          {{tab.group}}
          <template slot="dropdown">

              {{subTab.title}}

          </template>
        </dropdown>

      </template>

        <slot name="nav-right"/>

      <slot/>

</template>

<template>

      <template v-for="(tab, index) in groupedTabs">
        <dropdown v-if="tab.tabs" role="presentation" tag="li" :class="getTabClasses(tab)">
          {{tab.group}}
          <template slot="dropdown">

              {{subTab.title}}

          </template>
        </dropdown>

            <template v-else>{{tab.title}}</template>

      </template>

        <slot name="nav-right"/>

      <slot/>

</template>


Time controller doesn't auto update time.

<template>

    <q-resize-observer @resize="onResize" />

      <k-time-pointer
        :position="position"
        :time="currentValue"
        :formatter="timeFormatter"
        :componentLeft="componentLeft"
        :componentWidth="componentWidth"
        :pointerColor="pointerColor"
        :pointerTextColor="pointerTextColor"
        @change="onChangePosition"
        @changePointer="onChangePointer"
      />

      <k-time-indicator
        :position="timeIndicatorPosition"
        :time="timeIndicatorValue"
        :visible="timeIndicatorIsVisible"
        :formatter="timeFormatter"
        :componentLeft="componentLeft"
        :componentWidth="componentWidth"
        :color="color"
        :textColor="pointerTextColor"
        :timePointerLeft="timePointerLeft"
        :timePointerRight="timePointerRight"
        :timePointerHeight="timePointerHeight"
      />

      <k-time-interval
        v-for="interval in timeIntervals" :key="interval.value"
        :color="color"
        :interval="interval"
        :formatter="timeFormatter"
        :intervalDisplayWidth="intervalDisplayWidth"
        :labelFontSize="labelFontSize"
      />

</template>


Show content kind filter by default

Show content kind filter by default

<template>

      <ui-select
        v-if="showContentKindFilter"
        class="filter"
        :label="$tr('contentKinds')"
        :options="contentKindFilterOptions"
        v-model="contentKindFilterSelection"
      />

      <ui-select
        v-if="showChannelFilter"
        class="filter"
        :label="$tr('channels')"
        :options="channelFilterOptions"
        v-model="channelFilterSelection"
      />

    <content-card
      v-for="content in contents"
      v-show="showContentCard(content)"
      :key="content.id"
      :title="content.title"
      :thumbnail="content.thumbnail"
      :class="{'grid-item': true, 'mobile': isMobile}"
      :kind="content.kind"
      :progress="content.progress"
      :link="genContentLink(content.id, content.kind)"/>

</template>