revert unnecessary changes
This commit is contained in:
		
							parent
							
								
									6471bec0d9
								
							
						
					
					
						commit
						262760d258
					
				
					 120 changed files with 2128 additions and 4290 deletions
				
			
		
							
								
								
									
										113
									
								
								src/App.vue
									
									
									
									
									
								
							
							
						
						
									
										113
									
								
								src/App.vue
									
									
									
									
									
								
							| 
						 | 
				
			
			@ -1,112 +1,51 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    id="app"
 | 
			
		||||
    :style="bgAppStyle"
 | 
			
		||||
  >
 | 
			
		||||
    <div
 | 
			
		||||
      class="app-bg-wrapper"
 | 
			
		||||
      :style="bgStyle"
 | 
			
		||||
    />
 | 
			
		||||
  <div id="app" v-bind:style="bgAppStyle">
 | 
			
		||||
    <div class="app-bg-wrapper" v-bind:style="bgStyle"></div>
 | 
			
		||||
    <MobileNav v-if="isMobileLayout" />
 | 
			
		||||
    <nav
 | 
			
		||||
      v-else
 | 
			
		||||
      id="nav"
 | 
			
		||||
      class="nav-bar container"
 | 
			
		||||
      @click="scrollToTop()"
 | 
			
		||||
    >
 | 
			
		||||
      <div
 | 
			
		||||
        class="logo"
 | 
			
		||||
        :style="logoBgStyle"
 | 
			
		||||
      >
 | 
			
		||||
        <div
 | 
			
		||||
          class="mask"
 | 
			
		||||
          :style="logoMaskStyle"
 | 
			
		||||
        />
 | 
			
		||||
        <img
 | 
			
		||||
          :src="logo"
 | 
			
		||||
          :style="logoStyle"
 | 
			
		||||
        >
 | 
			
		||||
    <nav v-else class='nav-bar container' @click="scrollToTop()" id="nav">
 | 
			
		||||
      <div class='logo' :style='logoBgStyle'>
 | 
			
		||||
        <div class='mask' :style='logoMaskStyle'></div>
 | 
			
		||||
        <img :src='logo' :style='logoStyle'>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="inner-nav">
 | 
			
		||||
        <div class="item">
 | 
			
		||||
          <router-link
 | 
			
		||||
            class="site-name"
 | 
			
		||||
            :to="{ name: 'root' }"
 | 
			
		||||
            active-class="home"
 | 
			
		||||
          >
 | 
			
		||||
            {{ sitename }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
      <div class='inner-nav'>
 | 
			
		||||
        <div class='item'>
 | 
			
		||||
          <router-link class="site-name" :to="{ name: 'root' }" active-class="home">{{sitename}}</router-link>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="item right">
 | 
			
		||||
          <user-finder
 | 
			
		||||
            class="button-icon nav-icon mobile-hidden"
 | 
			
		||||
            @toggled="onFinderToggled"
 | 
			
		||||
          />
 | 
			
		||||
          <router-link
 | 
			
		||||
            class="mobile-hidden"
 | 
			
		||||
            :to="{ name: 'settings'}"
 | 
			
		||||
          >
 | 
			
		||||
            <i
 | 
			
		||||
              class="button-icon icon-cog nav-icon"
 | 
			
		||||
              :title="$t('nav.preferences')"
 | 
			
		||||
            />
 | 
			
		||||
          </router-link>
 | 
			
		||||
          <a
 | 
			
		||||
            v-if="currentUser"
 | 
			
		||||
            href="#"
 | 
			
		||||
            class="mobile-hidden"
 | 
			
		||||
            @click.prevent="logout"
 | 
			
		||||
          ><i
 | 
			
		||||
            class="button-icon icon-logout nav-icon"
 | 
			
		||||
            :title="$t('login.logout')"
 | 
			
		||||
          /></a>
 | 
			
		||||
        <div class='item right'>
 | 
			
		||||
          <user-finder class="button-icon nav-icon mobile-hidden" @toggled="onFinderToggled"></user-finder>
 | 
			
		||||
          <router-link class="mobile-hidden" :to="{ name: 'settings'}"><i class="button-icon icon-cog nav-icon" :title="$t('nav.preferences')"></i></router-link>
 | 
			
		||||
          <a href="#" class="mobile-hidden" v-if="currentUser" @click.prevent="logout"><i class="button-icon icon-logout nav-icon" :title="$t('login.logout')"></i></a>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </nav>
 | 
			
		||||
    <div
 | 
			
		||||
      id="content"
 | 
			
		||||
      class="container"
 | 
			
		||||
    >
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="!isMobileLayout"
 | 
			
		||||
        class="sidebar-flexer mobile-hidden"
 | 
			
		||||
      >
 | 
			
		||||
    <div v-if="" class="container" id="content">
 | 
			
		||||
      <div class="sidebar-flexer mobile-hidden" v-if="!isMobileLayout">
 | 
			
		||||
        <div class="sidebar-bounds">
 | 
			
		||||
          <div class="sidebar-scroller">
 | 
			
		||||
            <div class="sidebar">
 | 
			
		||||
              <user-panel />
 | 
			
		||||
              <nav-panel />
 | 
			
		||||
              <instance-specific-panel v-if="showInstanceSpecificPanel" />
 | 
			
		||||
              <features-panel v-if="!currentUser && showFeaturesPanel" />
 | 
			
		||||
              <who-to-follow-panel v-if="currentUser && suggestionsEnabled" />
 | 
			
		||||
              <notifications v-if="currentUser" />
 | 
			
		||||
              <user-panel></user-panel>
 | 
			
		||||
              <nav-panel></nav-panel>
 | 
			
		||||
              <instance-specific-panel v-if="showInstanceSpecificPanel"></instance-specific-panel>
 | 
			
		||||
              <features-panel v-if="!currentUser && showFeaturesPanel"></features-panel>
 | 
			
		||||
              <who-to-follow-panel v-if="currentUser && suggestionsEnabled"></who-to-follow-panel>
 | 
			
		||||
              <notifications v-if="currentUser"></notifications>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="main">
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="!currentUser"
 | 
			
		||||
          class="login-hint panel panel-default"
 | 
			
		||||
        >
 | 
			
		||||
          <router-link
 | 
			
		||||
            :to="{ name: 'login' }"
 | 
			
		||||
            class="panel-body"
 | 
			
		||||
          >
 | 
			
		||||
        <div v-if="!currentUser" class="login-hint panel panel-default">
 | 
			
		||||
          <router-link :to="{ name: 'login' }" class="panel-body">
 | 
			
		||||
            {{ $t("login.hint") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </div>
 | 
			
		||||
        <transition name="fade">
 | 
			
		||||
          <router-view />
 | 
			
		||||
          <router-view></router-view>
 | 
			
		||||
        </transition>
 | 
			
		||||
      </div>
 | 
			
		||||
      <media-modal />
 | 
			
		||||
      <media-modal></media-modal>
 | 
			
		||||
    </div>
 | 
			
		||||
    <chat-panel
 | 
			
		||||
      v-if="currentUser && chat"
 | 
			
		||||
      :floating="true"
 | 
			
		||||
      class="floating-chat mobile-hidden"
 | 
			
		||||
    />
 | 
			
		||||
    <chat-panel :floating="true" v-if="currentUser && chat" class="floating-chat mobile-hidden"></chat-panel>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -24,8 +24,8 @@ export default (store) => {
 | 
			
		|||
      path: '/',
 | 
			
		||||
      redirect: _to => {
 | 
			
		||||
        return (store.state.users.currentUser
 | 
			
		||||
          ? store.state.instance.redirectRootLogin
 | 
			
		||||
          : store.state.instance.redirectRootNoLogin) || '/main/all'
 | 
			
		||||
                ? store.state.instance.redirectRootLogin
 | 
			
		||||
                : store.state.instance.redirectRootNoLogin) || '/main/all'
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    { name: 'public-external-timeline', path: '/main/all', component: PublicAndExternalTimeline },
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,8 +1,8 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="sidebar">
 | 
			
		||||
    <instance-specific-panel />
 | 
			
		||||
    <features-panel v-if="showFeaturesPanel" />
 | 
			
		||||
    <terms-of-service-panel />
 | 
			
		||||
    <instance-specific-panel></instance-specific-panel>
 | 
			
		||||
    <features-panel v-if="showFeaturesPanel"></features-panel>
 | 
			
		||||
    <terms-of-service-panel></terms-of-service-panel>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -51,7 +51,7 @@ const Attachment = {
 | 
			
		|||
    }
 | 
			
		||||
  },
 | 
			
		||||
  methods: {
 | 
			
		||||
    linkClicked ({ target }) {
 | 
			
		||||
    linkClicked ({target}) {
 | 
			
		||||
      if (target.tagName === 'A') {
 | 
			
		||||
        window.open(target.href, '_blank')
 | 
			
		||||
      }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,104 +1,54 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    v-if="usePlaceHolder"
 | 
			
		||||
    @click="openModal"
 | 
			
		||||
  >
 | 
			
		||||
    <a
 | 
			
		||||
  <div v-if="usePlaceHolder" @click="openModal">
 | 
			
		||||
    <a class="placeholder"
 | 
			
		||||
      v-if="type !== 'html'"
 | 
			
		||||
      class="placeholder"
 | 
			
		||||
      target="_blank"
 | 
			
		||||
      :href="attachment.url"
 | 
			
		||||
      target="_blank" :href="attachment.url"
 | 
			
		||||
    >
 | 
			
		||||
      [{{ nsfw ? "NSFW/" : "" }}{{ type.toUpperCase() }}]
 | 
			
		||||
      [{{nsfw ? "NSFW/" : ""}}{{type.toUpperCase()}}]
 | 
			
		||||
    </a>
 | 
			
		||||
  </div>
 | 
			
		||||
  <div
 | 
			
		||||
    v-else
 | 
			
		||||
    v-show="!isEmpty"
 | 
			
		||||
    class="attachment"
 | 
			
		||||
    v-else class="attachment"
 | 
			
		||||
    :class="{[type]: true, loading, 'fullwidth': fullwidth, 'nsfw-placeholder': hidden}"
 | 
			
		||||
    v-show="!isEmpty"
 | 
			
		||||
  >
 | 
			
		||||
    <a
 | 
			
		||||
      v-if="hidden"
 | 
			
		||||
      class="image-attachment"
 | 
			
		||||
      :href="attachment.url"
 | 
			
		||||
      @click.prevent="toggleHidden"
 | 
			
		||||
    >
 | 
			
		||||
      <img
 | 
			
		||||
        :key="nsfwImage"
 | 
			
		||||
        class="nsfw"
 | 
			
		||||
        :src="nsfwImage"
 | 
			
		||||
        :class="{'small': isSmall}"
 | 
			
		||||
      >
 | 
			
		||||
      <i
 | 
			
		||||
        v-if="type === 'video'"
 | 
			
		||||
        class="play-icon icon-play-circled"
 | 
			
		||||
      />
 | 
			
		||||
    <a class="image-attachment" v-if="hidden" :href="attachment.url" @click.prevent="toggleHidden">
 | 
			
		||||
      <img class="nsfw" :key="nsfwImage" :src="nsfwImage" :class="{'small': isSmall}"/>
 | 
			
		||||
      <i v-if="type === 'video'" class="play-icon icon-play-circled"></i>
 | 
			
		||||
    </a>
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="nsfw && hideNsfwLocal && !hidden"
 | 
			
		||||
      class="hider"
 | 
			
		||||
    >
 | 
			
		||||
      <a
 | 
			
		||||
        href="#"
 | 
			
		||||
        @click.prevent="toggleHidden"
 | 
			
		||||
      >Hide</a>
 | 
			
		||||
    <div class="hider" v-if="nsfw && hideNsfwLocal && !hidden">
 | 
			
		||||
      <a href="#" @click.prevent="toggleHidden">Hide</a>
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <a
 | 
			
		||||
      v-if="type === 'image' && (!hidden || preloadImage)"
 | 
			
		||||
    <a v-if="type === 'image' && (!hidden || preloadImage)"
 | 
			
		||||
      @click="openModal"
 | 
			
		||||
      class="image-attachment"
 | 
			
		||||
      :class="{'hidden': hidden && preloadImage }"
 | 
			
		||||
      :href="attachment.url"
 | 
			
		||||
      target="_blank"
 | 
			
		||||
      :href="attachment.url" target="_blank"
 | 
			
		||||
      :title="attachment.description"
 | 
			
		||||
      @click="openModal"
 | 
			
		||||
    >
 | 
			
		||||
      <StillImage
 | 
			
		||||
        :referrerpolicy="referrerpolicy"
 | 
			
		||||
        :mimetype="attachment.mimetype"
 | 
			
		||||
        :src="attachment.large_thumb_url || attachment.url"
 | 
			
		||||
      />
 | 
			
		||||
      <StillImage :referrerpolicy="referrerpolicy" :mimetype="attachment.mimetype" :src="attachment.large_thumb_url || attachment.url"/>
 | 
			
		||||
    </a>
 | 
			
		||||
 | 
			
		||||
    <a
 | 
			
		||||
    <a class="video-container"
 | 
			
		||||
      @click="openModal"
 | 
			
		||||
      v-if="type === 'video' && !hidden"
 | 
			
		||||
      class="video-container"
 | 
			
		||||
      :class="{'small': isSmall}"
 | 
			
		||||
      :href="allowPlay ? undefined : attachment.url"
 | 
			
		||||
      @click="openModal"
 | 
			
		||||
    >
 | 
			
		||||
      <VideoAttachment
 | 
			
		||||
        class="video"
 | 
			
		||||
        :attachment="attachment"
 | 
			
		||||
        :controls="allowPlay"
 | 
			
		||||
      />
 | 
			
		||||
      <i
 | 
			
		||||
        v-if="!allowPlay"
 | 
			
		||||
        class="play-icon icon-play-circled"
 | 
			
		||||
      />
 | 
			
		||||
      <VideoAttachment class="video" :attachment="attachment" :controls="allowPlay" />
 | 
			
		||||
      <i v-if="!allowPlay" class="play-icon icon-play-circled"></i>
 | 
			
		||||
    </a>
 | 
			
		||||
 | 
			
		||||
    <audio
 | 
			
		||||
      v-if="type === 'audio'"
 | 
			
		||||
      :src="attachment.url"
 | 
			
		||||
      controls
 | 
			
		||||
    />
 | 
			
		||||
    <audio v-if="type === 'audio'" :src="attachment.url" controls></audio>
 | 
			
		||||
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="type === 'html' && attachment.oembed"
 | 
			
		||||
      class="oembed"
 | 
			
		||||
      @click.prevent="linkClicked"
 | 
			
		||||
    >
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="attachment.thumb_url"
 | 
			
		||||
        class="image"
 | 
			
		||||
      >
 | 
			
		||||
        <img :src="attachment.thumb_url">
 | 
			
		||||
    <div @click.prevent="linkClicked" v-if="type === 'html' && attachment.oembed" class="oembed">
 | 
			
		||||
      <div v-if="attachment.thumb_url" class="image">
 | 
			
		||||
        <img :src="attachment.thumb_url"/>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="text">
 | 
			
		||||
        <h1><a :href="attachment.url">{{ attachment.oembed.title }}</a></h1>
 | 
			
		||||
        <div v-html="attachment.oembed.oembedHTML" />
 | 
			
		||||
        <h1><a :href="attachment.url">{{attachment.oembed.title}}</a></h1>
 | 
			
		||||
        <div v-html="attachment.oembed.oembedHTML"></div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,49 +1,22 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="basic-user-card">
 | 
			
		||||
    <router-link :to="userProfileLink(user)">
 | 
			
		||||
      <UserAvatar
 | 
			
		||||
        class="avatar"
 | 
			
		||||
        :src="user.profile_image_url"
 | 
			
		||||
        @click.prevent.native="toggleUserExpanded"
 | 
			
		||||
      />
 | 
			
		||||
      <UserAvatar class="avatar" @click.prevent.native="toggleUserExpanded" :src="user.profile_image_url"/>
 | 
			
		||||
    </router-link>
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="userExpanded"
 | 
			
		||||
      class="basic-user-card-expanded-content"
 | 
			
		||||
    >
 | 
			
		||||
      <UserCard
 | 
			
		||||
        :user="user"
 | 
			
		||||
        :rounded="true"
 | 
			
		||||
        :bordered="true"
 | 
			
		||||
      />
 | 
			
		||||
    <div class="basic-user-card-expanded-content" v-if="userExpanded">
 | 
			
		||||
      <UserCard :user="user" :rounded="true" :bordered="true"/>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div
 | 
			
		||||
      v-else
 | 
			
		||||
      class="basic-user-card-collapsed-content"
 | 
			
		||||
    >
 | 
			
		||||
      <div
 | 
			
		||||
        :title="user.name"
 | 
			
		||||
        class="basic-user-card-user-name"
 | 
			
		||||
      >
 | 
			
		||||
        <span
 | 
			
		||||
          v-if="user.name_html"
 | 
			
		||||
          class="basic-user-card-user-name-value"
 | 
			
		||||
          v-html="user.name_html"
 | 
			
		||||
        />
 | 
			
		||||
        <span
 | 
			
		||||
          v-else
 | 
			
		||||
          class="basic-user-card-user-name-value"
 | 
			
		||||
        >{{ user.name }}</span>
 | 
			
		||||
    <div class="basic-user-card-collapsed-content" v-else>
 | 
			
		||||
      <div :title="user.name" class="basic-user-card-user-name">
 | 
			
		||||
        <span v-if="user.name_html" class="basic-user-card-user-name-value" v-html="user.name_html"></span>
 | 
			
		||||
        <span v-else class="basic-user-card-user-name-value">{{ user.name }}</span>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div>
 | 
			
		||||
        <router-link
 | 
			
		||||
          class="basic-user-card-screen-name"
 | 
			
		||||
          :to="userProfileLink(user)"
 | 
			
		||||
        >
 | 
			
		||||
          @{{ user.screen_name }}
 | 
			
		||||
        <router-link class="basic-user-card-screen-name" :to="userProfileLink(user)">
 | 
			
		||||
          @{{user.screen_name}}
 | 
			
		||||
        </router-link>
 | 
			
		||||
      </div>
 | 
			
		||||
      <slot />
 | 
			
		||||
      <slot></slot>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,12 +1,7 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <basic-user-card :user="user">
 | 
			
		||||
    <div class="block-card-content-container">
 | 
			
		||||
      <button
 | 
			
		||||
        v-if="blocked"
 | 
			
		||||
        class="btn btn-default"
 | 
			
		||||
        :disabled="progress"
 | 
			
		||||
        @click="unblockUser"
 | 
			
		||||
      >
 | 
			
		||||
      <button class="btn btn-default" @click="unblockUser" :disabled="progress" v-if="blocked">
 | 
			
		||||
        <template v-if="progress">
 | 
			
		||||
          {{ $t('user_card.unblock_progress') }}
 | 
			
		||||
        </template>
 | 
			
		||||
| 
						 | 
				
			
			@ -14,12 +9,7 @@
 | 
			
		|||
          {{ $t('user_card.unblock') }}
 | 
			
		||||
        </template>
 | 
			
		||||
      </button>
 | 
			
		||||
      <button
 | 
			
		||||
        v-else
 | 
			
		||||
        class="btn btn-default"
 | 
			
		||||
        :disabled="progress"
 | 
			
		||||
        @click="blockUser"
 | 
			
		||||
      >
 | 
			
		||||
      <button class="btn btn-default" @click="blockUser" :disabled="progress" v-else>
 | 
			
		||||
        <template v-if="progress">
 | 
			
		||||
          {{ $t('user_card.block_progress') }}
 | 
			
		||||
        </template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -16,7 +16,7 @@ const chatPanel = {
 | 
			
		|||
  },
 | 
			
		||||
  methods: {
 | 
			
		||||
    submit (message) {
 | 
			
		||||
      this.$store.state.chat.channel.push('new_msg', { text: message }, 10000)
 | 
			
		||||
      this.$store.state.chat.channel.push('new_msg', {text: message}, 10000)
 | 
			
		||||
      this.currentMessage = ''
 | 
			
		||||
    },
 | 
			
		||||
    togglePanel () {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,70 +1,41 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    v-if="!this.collapsed || !this.floating"
 | 
			
		||||
    class="chat-panel"
 | 
			
		||||
  >
 | 
			
		||||
  <div class="chat-panel" v-if="!this.collapsed || !this.floating">
 | 
			
		||||
    <div class="panel panel-default">
 | 
			
		||||
      <div
 | 
			
		||||
        class="panel-heading timeline-heading"
 | 
			
		||||
        :class="{ 'chat-heading': floating }"
 | 
			
		||||
        @click.stop.prevent="togglePanel"
 | 
			
		||||
      >
 | 
			
		||||
      <div class="panel-heading timeline-heading" :class="{ 'chat-heading': floating }" @click.stop.prevent="togglePanel">
 | 
			
		||||
        <div class="title">
 | 
			
		||||
          <span>{{ $t('chat.title') }}</span>
 | 
			
		||||
          <i
 | 
			
		||||
            v-if="floating"
 | 
			
		||||
            class="icon-cancel"
 | 
			
		||||
          />
 | 
			
		||||
          <span>{{$t('chat.title')}}</span>
 | 
			
		||||
          <i class="icon-cancel" v-if="floating"></i>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-chat-scroll
 | 
			
		||||
        class="chat-window"
 | 
			
		||||
      >
 | 
			
		||||
        <div
 | 
			
		||||
          v-for="message in messages"
 | 
			
		||||
          :key="message.id"
 | 
			
		||||
          class="chat-message"
 | 
			
		||||
        >
 | 
			
		||||
      <div class="chat-window" v-chat-scroll>
 | 
			
		||||
        <div class="chat-message" v-for="message in messages" :key="message.id">
 | 
			
		||||
          <span class="chat-avatar">
 | 
			
		||||
            <img :src="message.author.avatar">
 | 
			
		||||
            <img :src="message.author.avatar" />
 | 
			
		||||
          </span>
 | 
			
		||||
          <div class="chat-content">
 | 
			
		||||
            <router-link
 | 
			
		||||
              class="chat-name"
 | 
			
		||||
              :to="userProfileLink(message.author)"
 | 
			
		||||
            >
 | 
			
		||||
              {{ message.author.username }}
 | 
			
		||||
              :to="userProfileLink(message.author)">
 | 
			
		||||
                {{message.author.username}}
 | 
			
		||||
            </router-link>
 | 
			
		||||
            <br>
 | 
			
		||||
            <span class="chat-text">
 | 
			
		||||
              {{ message.text }}
 | 
			
		||||
              {{message.text}}
 | 
			
		||||
            </span>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="chat-input">
 | 
			
		||||
        <textarea
 | 
			
		||||
          v-model="currentMessage"
 | 
			
		||||
          class="chat-input-textarea"
 | 
			
		||||
          rows="1"
 | 
			
		||||
          @keyup.enter="submit(currentMessage)"
 | 
			
		||||
        />
 | 
			
		||||
        <textarea @keyup.enter="submit(currentMessage)" v-model="currentMessage" class="chat-input-textarea" rows="1"></textarea>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
  <div
 | 
			
		||||
    v-else
 | 
			
		||||
    class="chat-panel"
 | 
			
		||||
  >
 | 
			
		||||
  <div v-else class="chat-panel">
 | 
			
		||||
    <div class="panel panel-default">
 | 
			
		||||
      <div
 | 
			
		||||
        class="panel-heading stub timeline-heading chat-heading"
 | 
			
		||||
        @click.stop.prevent="togglePanel"
 | 
			
		||||
      >
 | 
			
		||||
      <div class="panel-heading stub timeline-heading chat-heading" @click.stop.prevent="togglePanel">
 | 
			
		||||
        <div class="title">
 | 
			
		||||
          <i class="icon-comment-empty" />
 | 
			
		||||
          {{ $t('chat.title') }}
 | 
			
		||||
          <i class="icon-comment-empty"></i>
 | 
			
		||||
          {{$t('chat.title')}}
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,44 +1,33 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="color-control style-control"
 | 
			
		||||
    :class="{ disabled: !present || disabled }"
 | 
			
		||||
  >
 | 
			
		||||
    <label
 | 
			
		||||
      :for="name"
 | 
			
		||||
      class="label"
 | 
			
		||||
<div class="color-control style-control" :class="{ disabled: !present || disabled }">
 | 
			
		||||
  <label :for="name" class="label">
 | 
			
		||||
    {{label}}
 | 
			
		||||
  </label>
 | 
			
		||||
  <input
 | 
			
		||||
    v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
    class="opt exlcude-disabled"
 | 
			
		||||
    :id="name + '-o'"
 | 
			
		||||
    type="checkbox"
 | 
			
		||||
    :checked="present"
 | 
			
		||||
    @input="$emit('input', typeof value === 'undefined' ? fallback : undefined)">
 | 
			
		||||
  <label v-if="typeof fallback !== 'undefined'" class="opt-l" :for="name + '-o'"></label>
 | 
			
		||||
  <input
 | 
			
		||||
    :id="name"
 | 
			
		||||
    class="color-input"
 | 
			
		||||
    type="color"
 | 
			
		||||
    :value="value || fallback"
 | 
			
		||||
    :disabled="!present || disabled"
 | 
			
		||||
    @input="$emit('input', $event.target.value)"
 | 
			
		||||
    >
 | 
			
		||||
      {{ label }}
 | 
			
		||||
    </label>
 | 
			
		||||
    <input
 | 
			
		||||
      v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
      :id="name + '-o'"
 | 
			
		||||
      class="opt exlcude-disabled"
 | 
			
		||||
      type="checkbox"
 | 
			
		||||
      :checked="present"
 | 
			
		||||
      @input="$emit('input', typeof value === 'undefined' ? fallback : undefined)"
 | 
			
		||||
  <input
 | 
			
		||||
    :id="name + '-t'"
 | 
			
		||||
    class="text-input"
 | 
			
		||||
    type="text"
 | 
			
		||||
    :value="value || fallback"
 | 
			
		||||
    :disabled="!present || disabled"
 | 
			
		||||
    @input="$emit('input', $event.target.value)"
 | 
			
		||||
    >
 | 
			
		||||
    <label
 | 
			
		||||
      v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
      class="opt-l"
 | 
			
		||||
      :for="name + '-o'"
 | 
			
		||||
    />
 | 
			
		||||
    <input
 | 
			
		||||
      :id="name"
 | 
			
		||||
      class="color-input"
 | 
			
		||||
      type="color"
 | 
			
		||||
      :value="value || fallback"
 | 
			
		||||
      :disabled="!present || disabled"
 | 
			
		||||
      @input="$emit('input', $event.target.value)"
 | 
			
		||||
    >
 | 
			
		||||
    <input
 | 
			
		||||
      :id="name + '-t'"
 | 
			
		||||
      class="text-input"
 | 
			
		||||
      type="text"
 | 
			
		||||
      :value="value || fallback"
 | 
			
		||||
      :disabled="!present || disabled"
 | 
			
		||||
      @input="$emit('input', $event.target.value)"
 | 
			
		||||
    >
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,38 +1,28 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <span
 | 
			
		||||
    v-if="contrast"
 | 
			
		||||
    class="contrast-ratio"
 | 
			
		||||
  >
 | 
			
		||||
    <span
 | 
			
		||||
      :title="hint"
 | 
			
		||||
      class="rating"
 | 
			
		||||
    >
 | 
			
		||||
      <span v-if="contrast.aaa">
 | 
			
		||||
        <i class="icon-thumbs-up-alt" />
 | 
			
		||||
      </span>
 | 
			
		||||
      <span v-if="!contrast.aaa && contrast.aa">
 | 
			
		||||
        <i class="icon-adjust" />
 | 
			
		||||
      </span>
 | 
			
		||||
      <span v-if="!contrast.aaa && !contrast.aa">
 | 
			
		||||
        <i class="icon-attention" />
 | 
			
		||||
      </span>
 | 
			
		||||
<span  v-if="contrast" class="contrast-ratio">
 | 
			
		||||
  <span :title="hint" class="rating">
 | 
			
		||||
    <span v-if="contrast.aaa">
 | 
			
		||||
      <i class="icon-thumbs-up-alt"/>
 | 
			
		||||
    </span>
 | 
			
		||||
    <span
 | 
			
		||||
      v-if="contrast && large"
 | 
			
		||||
      class="rating"
 | 
			
		||||
      :title="hint_18pt"
 | 
			
		||||
    >
 | 
			
		||||
      <span v-if="contrast.laaa">
 | 
			
		||||
        <i class="icon-thumbs-up-alt" />
 | 
			
		||||
      </span>
 | 
			
		||||
      <span v-if="!contrast.laaa && contrast.laa">
 | 
			
		||||
        <i class="icon-adjust" />
 | 
			
		||||
      </span>
 | 
			
		||||
      <span v-if="!contrast.laaa && !contrast.laa">
 | 
			
		||||
        <i class="icon-attention" />
 | 
			
		||||
      </span>
 | 
			
		||||
    <span v-if="!contrast.aaa && contrast.aa">
 | 
			
		||||
      <i class="icon-adjust"/>
 | 
			
		||||
    </span>
 | 
			
		||||
    <span v-if="!contrast.aaa && !contrast.aa">
 | 
			
		||||
      <i class="icon-attention"/>
 | 
			
		||||
    </span>
 | 
			
		||||
  </span>
 | 
			
		||||
  <span class="rating" v-if="contrast && large" :title="hint_18pt">
 | 
			
		||||
    <span v-if="contrast.laaa">
 | 
			
		||||
      <i class="icon-thumbs-up-alt"/>
 | 
			
		||||
    </span>
 | 
			
		||||
    <span v-if="!contrast.laaa && contrast.laa">
 | 
			
		||||
      <i class="icon-adjust"/>
 | 
			
		||||
    </span>
 | 
			
		||||
    <span v-if="!contrast.laaa && !contrast.laa">
 | 
			
		||||
      <i class="icon-attention"/>
 | 
			
		||||
    </span>
 | 
			
		||||
  </span>
 | 
			
		||||
</span>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,9 +1,9 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <conversation
 | 
			
		||||
    :collapsable="false"
 | 
			
		||||
    is-page="true"
 | 
			
		||||
    isPage="true"
 | 
			
		||||
    :statusoid="statusoid"
 | 
			
		||||
  />
 | 
			
		||||
  ></conversation>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./conversation-page.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -94,8 +94,8 @@ const conversation = {
 | 
			
		|||
    },
 | 
			
		||||
    replies () {
 | 
			
		||||
      let i = 1
 | 
			
		||||
      /* eslint-disable camelcase */
 | 
			
		||||
      return reduce(this.conversation, (result, { id, in_reply_to_status_id }) => {
 | 
			
		||||
      return reduce(this.conversation, (result, {id, in_reply_to_status_id}) => {
 | 
			
		||||
        /* eslint-disable camelcase */
 | 
			
		||||
        const irid = in_reply_to_status_id
 | 
			
		||||
        /* eslint-enable camelcase */
 | 
			
		||||
        if (irid) {
 | 
			
		||||
| 
						 | 
				
			
			@ -127,8 +127,8 @@ const conversation = {
 | 
			
		|||
  methods: {
 | 
			
		||||
    fetchConversation () {
 | 
			
		||||
      if (this.status) {
 | 
			
		||||
        this.$store.state.api.backendInteractor.fetchConversation({ id: this.status.id })
 | 
			
		||||
          .then(({ ancestors, descendants }) => {
 | 
			
		||||
        this.$store.state.api.backendInteractor.fetchConversation({id: this.status.id})
 | 
			
		||||
          .then(({ancestors, descendants}) => {
 | 
			
		||||
            this.$store.dispatch('addNewStatuses', { statuses: ancestors })
 | 
			
		||||
            this.$store.dispatch('addNewStatuses', { statuses: descendants })
 | 
			
		||||
            set(this, 'converationStatusIds', [].concat(
 | 
			
		||||
| 
						 | 
				
			
			@ -139,7 +139,7 @@ const conversation = {
 | 
			
		|||
          .then(() => this.setHighlight(this.statusId))
 | 
			
		||||
      } else {
 | 
			
		||||
        const id = this.$route.params.id
 | 
			
		||||
        this.$store.state.api.backendInteractor.fetchStatus({ id })
 | 
			
		||||
        this.$store.state.api.backendInteractor.fetchStatus({id})
 | 
			
		||||
          .then((status) => this.$store.dispatch('addNewStatuses', { statuses: [status] }))
 | 
			
		||||
          .then(() => this.fetchConversation())
 | 
			
		||||
      }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,33 +1,24 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="timeline panel-default"
 | 
			
		||||
    :class="[isExpanded ? 'panel' : 'panel-disabled']"
 | 
			
		||||
  >
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="isExpanded"
 | 
			
		||||
      class="panel-heading conversation-heading"
 | 
			
		||||
    >
 | 
			
		||||
  <div class="timeline panel-default" :class="[isExpanded ? 'panel' : 'panel-disabled']">
 | 
			
		||||
    <div v-if="isExpanded" class="panel-heading conversation-heading">
 | 
			
		||||
      <span class="title"> {{ $t('timeline.conversation') }} </span>
 | 
			
		||||
      <span v-if="collapsable">
 | 
			
		||||
        <a
 | 
			
		||||
          href="#"
 | 
			
		||||
          @click.prevent="toggleExpanded"
 | 
			
		||||
        >{{ $t('timeline.collapse') }}</a>
 | 
			
		||||
        <a href="#" @click.prevent="toggleExpanded">{{ $t('timeline.collapse') }}</a>
 | 
			
		||||
      </span>
 | 
			
		||||
    </div>
 | 
			
		||||
    <status
 | 
			
		||||
      v-for="status in conversation"
 | 
			
		||||
      @goto="setHighlight"
 | 
			
		||||
      @toggleExpanded="toggleExpanded"
 | 
			
		||||
      :key="status.id"
 | 
			
		||||
      :inline-expanded="collapsable"
 | 
			
		||||
      :inlineExpanded="collapsable"
 | 
			
		||||
      :statusoid="status"
 | 
			
		||||
      :expandable="!expanded"
 | 
			
		||||
      :expandable='!expanded'
 | 
			
		||||
      :focused="focused(status.id)"
 | 
			
		||||
      :in-conversation="isExpanded"
 | 
			
		||||
      :inConversation="isExpanded"
 | 
			
		||||
      :highlight="getHighlight()"
 | 
			
		||||
      :replies="getReplies(status.id)"
 | 
			
		||||
      class="status-fadein panel-body"
 | 
			
		||||
      @goto="setHighlight"
 | 
			
		||||
      @toggleExpanded="toggleExpanded"
 | 
			
		||||
    />
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -10,7 +10,7 @@ const DeleteButton = {
 | 
			
		|||
  },
 | 
			
		||||
  computed: {
 | 
			
		||||
    currentUser () { return this.$store.state.users.currentUser },
 | 
			
		||||
    canDelete () { return (this.currentUser && this.currentUser.rights.delete_others_notice) || this.status.user.id === this.currentUser.id }
 | 
			
		||||
    canDelete () { return this.currentUser && this.currentUser.rights.delete_others_notice || this.status.user.id === this.currentUser.id }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,10 +1,7 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div v-if="canDelete">
 | 
			
		||||
    <a
 | 
			
		||||
      href="#"
 | 
			
		||||
      @click.prevent="deleteStatus()"
 | 
			
		||||
    >
 | 
			
		||||
      <i class="button-icon icon-cancel delete-status" />
 | 
			
		||||
    <a href="#" v-on:click.prevent="deleteStatus()">
 | 
			
		||||
      <i class='button-icon icon-cancel delete-status'></i>
 | 
			
		||||
    </a>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,9 +1,5 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <Timeline
 | 
			
		||||
    :title="$t('nav.dms')"
 | 
			
		||||
    :timeline="timeline"
 | 
			
		||||
    :timeline-name="'dms'"
 | 
			
		||||
  />
 | 
			
		||||
  <Timeline :title="$t('nav.dms')" v-bind:timeline="timeline" v-bind:timeline-name="'dms'"/>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./dm_timeline.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -23,8 +23,7 @@ const EmojiInput = {
 | 
			
		|||
        if (matchedEmoji.length <= 0) {
 | 
			
		||||
          return false
 | 
			
		||||
        }
 | 
			
		||||
        // eslint-disable-next-line camelcase
 | 
			
		||||
        return map(take(matchedEmoji, 5), ({ shortcode, image_url, utf }, index) => ({
 | 
			
		||||
        return map(take(matchedEmoji, 5), ({shortcode, image_url, utf}, index) => ({
 | 
			
		||||
          shortcode: `:${shortcode}:`,
 | 
			
		||||
          utf: utf || '',
 | 
			
		||||
          // eslint-disable-next-line camelcase
 | 
			
		||||
| 
						 | 
				
			
			@ -99,7 +98,7 @@ const EmojiInput = {
 | 
			
		|||
    onInput (e) {
 | 
			
		||||
      this.$emit('input', e.target.value)
 | 
			
		||||
    },
 | 
			
		||||
    setCaret ({ target: { selectionStart } }) {
 | 
			
		||||
    setCaret ({target: {selectionStart}}) {
 | 
			
		||||
      this.caret = selectionStart
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -9,13 +9,13 @@
 | 
			
		|||
      @input="onInput"
 | 
			
		||||
      @click="setCaret"
 | 
			
		||||
      @keyup="setCaret"
 | 
			
		||||
      @keydown.exact="onKeydown"
 | 
			
		||||
      @keydown.down.exact="cycleForward"
 | 
			
		||||
      @keydown.up.exact="cycleBackward"
 | 
			
		||||
      @keydown.shift.tab.exact="cycleBackward"
 | 
			
		||||
      @keydown.tab.exact="cycleForward"
 | 
			
		||||
      @keydown.enter.exact="replaceEmoji"
 | 
			
		||||
    >
 | 
			
		||||
      @keydown="onKeydown"
 | 
			
		||||
      @keydown.down="cycleForward"
 | 
			
		||||
      @keydown.up="cycleBackward"
 | 
			
		||||
      @keydown.shift.tab="cycleBackward"
 | 
			
		||||
      @keydown.tab="cycleForward"
 | 
			
		||||
      @keydown.enter="replaceEmoji"
 | 
			
		||||
    />
 | 
			
		||||
    <textarea
 | 
			
		||||
      v-else
 | 
			
		||||
      :class="classname"
 | 
			
		||||
| 
						 | 
				
			
			@ -24,30 +24,27 @@
 | 
			
		|||
      @input="onInput"
 | 
			
		||||
      @click="setCaret"
 | 
			
		||||
      @keyup="setCaret"
 | 
			
		||||
      @keydown.exact="onKeydown"
 | 
			
		||||
      @keydown.down.exact="cycleForward"
 | 
			
		||||
      @keydown.up.exact="cycleBackward"
 | 
			
		||||
      @keydown.shift.tab.exact="cycleBackward"
 | 
			
		||||
      @keydown.tab.exact="cycleForward"
 | 
			
		||||
      @keydown.enter.exact="replaceEmoji"
 | 
			
		||||
    />
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="suggestions"
 | 
			
		||||
      class="autocomplete-panel"
 | 
			
		||||
    >
 | 
			
		||||
      @keydown="onKeydown"
 | 
			
		||||
      @keydown.down="cycleForward"
 | 
			
		||||
      @keydown.up="cycleBackward"
 | 
			
		||||
      @keydown.shift.tab="cycleBackward"
 | 
			
		||||
      @keydown.tab="cycleForward"
 | 
			
		||||
      @keydown.enter="replaceEmoji"
 | 
			
		||||
    ></textarea>
 | 
			
		||||
    <div class="autocomplete-panel" v-if="suggestions">
 | 
			
		||||
      <div class="autocomplete-panel-body">
 | 
			
		||||
        <div
 | 
			
		||||
          v-for="(emoji, index) in suggestions"
 | 
			
		||||
          :key="index"
 | 
			
		||||
          @click="replace(emoji.utf || (emoji.shortcode + ' '))"
 | 
			
		||||
          class="autocomplete-item"
 | 
			
		||||
          :class="{ highlighted: emoji.highlighted }"
 | 
			
		||||
          @click="replace(emoji.utf || (emoji.shortcode + ' '))"
 | 
			
		||||
        >
 | 
			
		||||
          <span v-if="emoji.img">
 | 
			
		||||
            <img :src="emoji.img">
 | 
			
		||||
            <img :src="emoji.img" />
 | 
			
		||||
          </span>
 | 
			
		||||
          <span v-else>{{ emoji.utf }}</span>
 | 
			
		||||
          <span>{{ emoji.shortcode }}</span>
 | 
			
		||||
          <span v-else>{{emoji.utf}}</span>
 | 
			
		||||
          <span>{{emoji.shortcode}}</span>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,27 +1,12 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="import-export-container">
 | 
			
		||||
    <slot name="before" />
 | 
			
		||||
    <button
 | 
			
		||||
      class="btn"
 | 
			
		||||
      @click="exportData"
 | 
			
		||||
    >
 | 
			
		||||
      {{ exportLabel }}
 | 
			
		||||
    </button>
 | 
			
		||||
    <button
 | 
			
		||||
      class="btn"
 | 
			
		||||
      @click="importData"
 | 
			
		||||
    >
 | 
			
		||||
      {{ importLabel }}
 | 
			
		||||
    </button>
 | 
			
		||||
    <slot name="afterButtons" />
 | 
			
		||||
    <p
 | 
			
		||||
      v-if="importFailed"
 | 
			
		||||
      class="alert error"
 | 
			
		||||
    >
 | 
			
		||||
      {{ importFailedText }}
 | 
			
		||||
    </p>
 | 
			
		||||
    <slot name="afterError" />
 | 
			
		||||
  </div>
 | 
			
		||||
<div class="import-export-container">
 | 
			
		||||
  <slot name="before"/>
 | 
			
		||||
  <button class="btn" @click="exportData">{{ exportLabel }}</button>
 | 
			
		||||
  <button class="btn" @click="importData">{{ importLabel }}</button>
 | 
			
		||||
  <slot name="afterButtons"/>
 | 
			
		||||
  <p v-if="importFailed" class="alert error">{{ importFailedText }}</p>
 | 
			
		||||
  <slot name="afterError"/>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script>
 | 
			
		||||
| 
						 | 
				
			
			@ -64,7 +49,7 @@ export default {
 | 
			
		|||
        if (event.target.files[0]) {
 | 
			
		||||
          // eslint-disable-next-line no-undef
 | 
			
		||||
          const reader = new FileReader()
 | 
			
		||||
          reader.onload = ({ target }) => {
 | 
			
		||||
          reader.onload = ({target}) => {
 | 
			
		||||
            try {
 | 
			
		||||
              const parsed = JSON.parse(target.result)
 | 
			
		||||
              const valid = this.validator(parsed)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -11,9 +11,9 @@ const FavoriteButton = {
 | 
			
		|||
  methods: {
 | 
			
		||||
    favorite () {
 | 
			
		||||
      if (!this.status.favorited) {
 | 
			
		||||
        this.$store.dispatch('favorite', { id: this.status.id })
 | 
			
		||||
        this.$store.dispatch('favorite', {id: this.status.id})
 | 
			
		||||
      } else {
 | 
			
		||||
        this.$store.dispatch('unfavorite', { id: this.status.id })
 | 
			
		||||
        this.$store.dispatch('unfavorite', {id: this.status.id})
 | 
			
		||||
      }
 | 
			
		||||
      this.animated = true
 | 
			
		||||
      setTimeout(() => {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,20 +1,11 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div v-if="loggedIn">
 | 
			
		||||
    <i
 | 
			
		||||
      :class="classes"
 | 
			
		||||
      class="button-icon favorite-button fav-active"
 | 
			
		||||
      :title="$t('tool_tip.favorite')"
 | 
			
		||||
      @click.prevent="favorite()"
 | 
			
		||||
    />
 | 
			
		||||
    <span v-if="!hidePostStatsLocal && status.fave_num > 0">{{ status.fave_num }}</span>
 | 
			
		||||
    <i :class='classes' class='button-icon favorite-button fav-active' @click.prevent='favorite()' :title="$t('tool_tip.favorite')"/>
 | 
			
		||||
    <span v-if='!hidePostStatsLocal && status.fave_num > 0'>{{status.fave_num}}</span>
 | 
			
		||||
  </div>
 | 
			
		||||
  <div v-else>
 | 
			
		||||
    <i
 | 
			
		||||
      :class="classes"
 | 
			
		||||
      class="button-icon favorite-button"
 | 
			
		||||
      :title="$t('tool_tip.favorite')"
 | 
			
		||||
    />
 | 
			
		||||
    <span v-if="!hidePostStatsLocal && status.fave_num > 0">{{ status.fave_num }}</span>
 | 
			
		||||
    <i :class='classes' class='button-icon favorite-button' :title="$t('tool_tip.favorite')"/>
 | 
			
		||||
    <span v-if='!hidePostStatsLocal && status.fave_num > 0'>{{status.fave_num}}</span>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -3,25 +3,17 @@
 | 
			
		|||
    <div class="panel panel-default base01-background">
 | 
			
		||||
      <div class="panel-heading timeline-heading base02-background base04">
 | 
			
		||||
        <div class="title">
 | 
			
		||||
          {{ $t('features_panel.title') }}
 | 
			
		||||
          {{$t('features_panel.title')}}
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="panel-body features-panel">
 | 
			
		||||
        <ul>
 | 
			
		||||
          <li v-if="chat">
 | 
			
		||||
            {{ $t('features_panel.chat') }}
 | 
			
		||||
          </li>
 | 
			
		||||
          <li v-if="gopher">
 | 
			
		||||
            {{ $t('features_panel.gopher') }}
 | 
			
		||||
          </li>
 | 
			
		||||
          <li v-if="whoToFollow">
 | 
			
		||||
            {{ $t('features_panel.who_to_follow') }}
 | 
			
		||||
          </li>
 | 
			
		||||
          <li v-if="mediaProxy">
 | 
			
		||||
            {{ $t('features_panel.media_proxy') }}
 | 
			
		||||
          </li>
 | 
			
		||||
          <li>{{ $t('features_panel.scope_options') }}</li>
 | 
			
		||||
          <li>{{ $t('features_panel.text_limit') }} = {{ textlimit }}</li>
 | 
			
		||||
          <li v-if="chat">{{$t('features_panel.chat')}}</li>
 | 
			
		||||
          <li v-if="gopher">{{$t('features_panel.gopher')}}</li>
 | 
			
		||||
          <li v-if="whoToFollow">{{$t('features_panel.who_to_follow')}}</li>
 | 
			
		||||
          <li v-if="mediaProxy">{{$t('features_panel.media_proxy')}}</li>
 | 
			
		||||
          <li>{{$t('features_panel.scope_options')}}</li>
 | 
			
		||||
          <li>{{$t('features_panel.text_limit')}} = {{textlimit}}</li>
 | 
			
		||||
        </ul>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -22,7 +22,7 @@ const FollowCard = {
 | 
			
		|||
    isMe () { return this.$store.state.users.currentUser.id === this.user.id },
 | 
			
		||||
    following () { return this.updated ? this.updated.following : this.user.following },
 | 
			
		||||
    showFollow () {
 | 
			
		||||
      return !this.following || (this.updated && !this.updated.following)
 | 
			
		||||
      return !this.following || this.updated && !this.updated.following
 | 
			
		||||
    },
 | 
			
		||||
    loggedIn () {
 | 
			
		||||
      return this.$store.state.users.currentUser
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,24 +1,18 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <basic-user-card :user="user">
 | 
			
		||||
    <div class="follow-card-content-container">
 | 
			
		||||
      <span
 | 
			
		||||
        v-if="!noFollowsYou && user.follows_you"
 | 
			
		||||
        class="faint"
 | 
			
		||||
      >
 | 
			
		||||
      <span class="faint" v-if="!noFollowsYou && user.follows_you">
 | 
			
		||||
        {{ isMe ? $t('user_card.its_you') : $t('user_card.follows_you') }}
 | 
			
		||||
      </span>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="showFollow && !loggedIn"
 | 
			
		||||
        class="follow-card-follow-button"
 | 
			
		||||
      >
 | 
			
		||||
      <div class="follow-card-follow-button" v-if="showFollow && !loggedIn">
 | 
			
		||||
        <RemoteFollow :user="user" />
 | 
			
		||||
      </div>
 | 
			
		||||
      <button
 | 
			
		||||
        v-if="showFollow && loggedIn"
 | 
			
		||||
        class="btn btn-default follow-card-follow-button"
 | 
			
		||||
        @click="followUser"
 | 
			
		||||
        :disabled="inProgress"
 | 
			
		||||
        :title="requestSent ? $t('user_card.follow_again') : ''"
 | 
			
		||||
        @click="followUser"
 | 
			
		||||
      >
 | 
			
		||||
        <template v-if="inProgress">
 | 
			
		||||
          {{ $t('user_card.follow_progress') }}
 | 
			
		||||
| 
						 | 
				
			
			@ -30,12 +24,7 @@
 | 
			
		|||
          {{ $t('user_card.follow') }}
 | 
			
		||||
        </template>
 | 
			
		||||
      </button>
 | 
			
		||||
      <button
 | 
			
		||||
        v-if="following"
 | 
			
		||||
        class="btn btn-default follow-card-follow-button pressed"
 | 
			
		||||
        :disabled="inProgress"
 | 
			
		||||
        @click="unfollowUser"
 | 
			
		||||
      >
 | 
			
		||||
      <button v-if="following" class="btn btn-default follow-card-follow-button pressed" @click="unfollowUser" :disabled="inProgress">
 | 
			
		||||
        <template v-if="inProgress">
 | 
			
		||||
          {{ $t('user_card.follow_progress') }}
 | 
			
		||||
        </template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,18 +1,8 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <basic-user-card :user="user">
 | 
			
		||||
    <div class="follow-request-card-content-container">
 | 
			
		||||
      <button
 | 
			
		||||
        class="btn btn-default"
 | 
			
		||||
        @click="approveUser"
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('user_card.approve') }}
 | 
			
		||||
      </button>
 | 
			
		||||
      <button
 | 
			
		||||
        class="btn btn-default"
 | 
			
		||||
        @click="denyUser"
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('user_card.deny') }}
 | 
			
		||||
      </button>
 | 
			
		||||
      <button class="btn btn-default" @click="approveUser">{{ $t('user_card.approve') }}</button>
 | 
			
		||||
      <button class="btn btn-default" @click="denyUser">{{ $t('user_card.deny') }}</button>
 | 
			
		||||
    </div>
 | 
			
		||||
  </basic-user-card>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,14 +1,10 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="settings panel panel-default">
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      {{ $t('nav.friend_requests') }}
 | 
			
		||||
      {{$t('nav.friend_requests')}}
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="panel-body">
 | 
			
		||||
      <FollowRequestCard
 | 
			
		||||
        v-for="request in requests"
 | 
			
		||||
        :key="request.id"
 | 
			
		||||
        :user="request"
 | 
			
		||||
      />
 | 
			
		||||
      <FollowRequestCard v-for="request in requests" :key="request.id" :user="request"/>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,56 +1,35 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="font-control style-control"
 | 
			
		||||
    :class="{ custom: isCustom }"
 | 
			
		||||
  >
 | 
			
		||||
    <label
 | 
			
		||||
      :for="preset === 'custom' ? name : name + '-font-switcher'"
 | 
			
		||||
      class="label"
 | 
			
		||||
    >
 | 
			
		||||
      {{ label }}
 | 
			
		||||
    </label>
 | 
			
		||||
    <input
 | 
			
		||||
      v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
      :id="name + '-o'"
 | 
			
		||||
      class="opt exlcude-disabled"
 | 
			
		||||
      type="checkbox"
 | 
			
		||||
      :checked="present"
 | 
			
		||||
      @input="$emit('input', typeof value === 'undefined' ? fallback : undefined)"
 | 
			
		||||
    >
 | 
			
		||||
    <label
 | 
			
		||||
      v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
      class="opt-l"
 | 
			
		||||
      :for="name + '-o'"
 | 
			
		||||
    />
 | 
			
		||||
    <label
 | 
			
		||||
      :for="name + '-font-switcher'"
 | 
			
		||||
      class="select"
 | 
			
		||||
<div class="font-control style-control" :class="{ custom: isCustom }">
 | 
			
		||||
  <label :for="preset === 'custom' ? name : name + '-font-switcher'" class="label">
 | 
			
		||||
    {{label}}
 | 
			
		||||
  </label>
 | 
			
		||||
  <input
 | 
			
		||||
    v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
    class="opt exlcude-disabled"
 | 
			
		||||
    type="checkbox"
 | 
			
		||||
    :id="name + '-o'"
 | 
			
		||||
    :checked="present"
 | 
			
		||||
    @input="$emit('input', typeof value === 'undefined' ? fallback : undefined)">
 | 
			
		||||
  <label v-if="typeof fallback !== 'undefined'" class="opt-l" :for="name + '-o'"></label>
 | 
			
		||||
  <label :for="name + '-font-switcher'" class="select" :disabled="!present">
 | 
			
		||||
    <select
 | 
			
		||||
      :disabled="!present"
 | 
			
		||||
    >
 | 
			
		||||
      <select
 | 
			
		||||
        :id="name + '-font-switcher'"
 | 
			
		||||
        v-model="preset"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        class="font-switcher"
 | 
			
		||||
      >
 | 
			
		||||
        <option
 | 
			
		||||
          v-for="option in availableOptions"
 | 
			
		||||
          :key="option"
 | 
			
		||||
          :value="option"
 | 
			
		||||
        >
 | 
			
		||||
          {{ option === 'custom' ? $t('settings.style.fonts.custom') : option }}
 | 
			
		||||
        </option>
 | 
			
		||||
      </select>
 | 
			
		||||
      <i class="icon-down-open" />
 | 
			
		||||
    </label>
 | 
			
		||||
    <input
 | 
			
		||||
      v-if="isCustom"
 | 
			
		||||
      :id="name"
 | 
			
		||||
      v-model="family"
 | 
			
		||||
      class="custom-font"
 | 
			
		||||
      type="text"
 | 
			
		||||
    >
 | 
			
		||||
  </div>
 | 
			
		||||
      v-model="preset"
 | 
			
		||||
      class="font-switcher"
 | 
			
		||||
      :id="name + '-font-switcher'">
 | 
			
		||||
      <option v-for="option in availableOptions" :value="option">
 | 
			
		||||
        {{ option === 'custom' ? $t('settings.style.fonts.custom') : option }}
 | 
			
		||||
      </option>
 | 
			
		||||
    </select>
 | 
			
		||||
    <i class="icon-down-open"/>
 | 
			
		||||
  </label>
 | 
			
		||||
  <input
 | 
			
		||||
    v-if="isCustom"
 | 
			
		||||
    class="custom-font"
 | 
			
		||||
    type="text"
 | 
			
		||||
    :id="name"
 | 
			
		||||
    v-model="family">
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./font_control.js" ></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,9 +1,5 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <Timeline
 | 
			
		||||
    :title="$t('nav.timeline')"
 | 
			
		||||
    :timeline="timeline"
 | 
			
		||||
    :timeline-name="'friends'"
 | 
			
		||||
  />
 | 
			
		||||
  <Timeline :title="$t('nav.timeline')" v-bind:timeline="timeline" v-bind:timeline-name="'friends'"/>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./friends_timeline.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,22 +1,13 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    ref="galleryContainer"
 | 
			
		||||
    style="width: 100%;"
 | 
			
		||||
  >
 | 
			
		||||
    <div
 | 
			
		||||
      v-for="row in rows"
 | 
			
		||||
      :key="row"
 | 
			
		||||
      class="gallery-row"
 | 
			
		||||
      :style="rowHeight(row.length)"
 | 
			
		||||
      :class="{ 'contain-fit': useContainFit, 'cover-fit': !useContainFit }"
 | 
			
		||||
    >
 | 
			
		||||
  <div ref="galleryContainer" style="width: 100%;">
 | 
			
		||||
    <div class="gallery-row" v-for="row in rows" :style="rowHeight(row.length)" :class="{ 'contain-fit': useContainFit, 'cover-fit': !useContainFit }">
 | 
			
		||||
      <attachment
 | 
			
		||||
        v-for="attachment in row"
 | 
			
		||||
        :key="attachment.id"
 | 
			
		||||
        :set-media="setMedia"
 | 
			
		||||
        :setMedia="setMedia"
 | 
			
		||||
        :nsfw="nsfw"
 | 
			
		||||
        :attachment="attachment"
 | 
			
		||||
        :allow-play="false"
 | 
			
		||||
        :allowPlay="false"
 | 
			
		||||
        :key="attachment.id"
 | 
			
		||||
      />
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -2,57 +2,20 @@
 | 
			
		|||
  <div class="image-cropper">
 | 
			
		||||
    <div v-if="dataUrl">
 | 
			
		||||
      <div class="image-cropper-image-container">
 | 
			
		||||
        <img
 | 
			
		||||
          ref="img"
 | 
			
		||||
          :src="dataUrl"
 | 
			
		||||
          alt=""
 | 
			
		||||
          @load.stop="createCropper"
 | 
			
		||||
        >
 | 
			
		||||
        <img ref="img" :src="dataUrl" alt="" @load.stop="createCropper" />
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="image-cropper-buttons-wrapper">
 | 
			
		||||
        <button
 | 
			
		||||
          class="btn"
 | 
			
		||||
          type="button"
 | 
			
		||||
          :disabled="submitting"
 | 
			
		||||
          @click="submit"
 | 
			
		||||
          v-text="saveText"
 | 
			
		||||
        />
 | 
			
		||||
        <button
 | 
			
		||||
          class="btn"
 | 
			
		||||
          type="button"
 | 
			
		||||
          :disabled="submitting"
 | 
			
		||||
          @click="destroy"
 | 
			
		||||
          v-text="cancelText"
 | 
			
		||||
        />
 | 
			
		||||
        <button
 | 
			
		||||
          class="btn"
 | 
			
		||||
          type="button"
 | 
			
		||||
          :disabled="submitting"
 | 
			
		||||
          @click="submitWithoutCropping"
 | 
			
		||||
          v-text="saveWithoutCroppingText"
 | 
			
		||||
        />
 | 
			
		||||
        <i
 | 
			
		||||
          v-if="submitting"
 | 
			
		||||
          class="icon-spin4 animate-spin"
 | 
			
		||||
        />
 | 
			
		||||
        <button class="btn" type="button" :disabled="submitting" @click="submit" v-text="saveText"></button>
 | 
			
		||||
        <button class="btn" type="button" :disabled="submitting" @click="destroy" v-text="cancelText"></button>
 | 
			
		||||
        <button class="btn" type="button" :disabled="submitting" @click="submitWithoutCropping" v-text="saveWithoutCroppingText"></button>
 | 
			
		||||
        <i class="icon-spin4 animate-spin" v-if="submitting"></i>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="submitError"
 | 
			
		||||
        class="alert error"
 | 
			
		||||
      >
 | 
			
		||||
        {{ submitErrorMsg }}
 | 
			
		||||
        <i
 | 
			
		||||
          class="button-icon icon-cancel"
 | 
			
		||||
          @click="clearError"
 | 
			
		||||
        />
 | 
			
		||||
      <div class="alert error" v-if="submitError">
 | 
			
		||||
        {{submitErrorMsg}}
 | 
			
		||||
        <i class="button-icon icon-cancel" @click="clearError"></i>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <input
 | 
			
		||||
      ref="input"
 | 
			
		||||
      type="file"
 | 
			
		||||
      class="image-cropper-img-input"
 | 
			
		||||
      :accept="mimes"
 | 
			
		||||
    >
 | 
			
		||||
    <input ref="input" type="file" class="image-cropper-img-input" :accept="mimes">
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,11 +1,9 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    v-if="show"
 | 
			
		||||
    class="instance-specific-panel"
 | 
			
		||||
  >
 | 
			
		||||
  <div v-if="show" class="instance-specific-panel">
 | 
			
		||||
    <div class="panel panel-default">
 | 
			
		||||
      <div class="panel-body">
 | 
			
		||||
        <div v-html="instanceSpecificPanelContent" />
 | 
			
		||||
        <div v-html="instanceSpecificPanelContent">
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -3,49 +3,39 @@
 | 
			
		|||
    <label for="interface-language-switcher">
 | 
			
		||||
      {{ $t('settings.interfaceLanguage') }}
 | 
			
		||||
    </label>
 | 
			
		||||
    <label
 | 
			
		||||
      for="interface-language-switcher"
 | 
			
		||||
      class="select"
 | 
			
		||||
    >
 | 
			
		||||
      <select
 | 
			
		||||
        id="interface-language-switcher"
 | 
			
		||||
        v-model="language"
 | 
			
		||||
      >
 | 
			
		||||
        <option
 | 
			
		||||
          v-for="(langCode, i) in languageCodes"
 | 
			
		||||
          :key="langCode"
 | 
			
		||||
          :value="langCode"
 | 
			
		||||
        >
 | 
			
		||||
    <label for="interface-language-switcher" class='select'>
 | 
			
		||||
      <select id="interface-language-switcher" v-model="language">
 | 
			
		||||
        <option v-for="(langCode, i) in languageCodes" :value="langCode">
 | 
			
		||||
          {{ languageNames[i] }}
 | 
			
		||||
        </option>
 | 
			
		||||
      </select>
 | 
			
		||||
      <i class="icon-down-open" />
 | 
			
		||||
      <i class="icon-down-open"/>
 | 
			
		||||
    </label>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script>
 | 
			
		||||
import languagesObject from '../../i18n/messages'
 | 
			
		||||
import ISO6391 from 'iso-639-1'
 | 
			
		||||
import _ from 'lodash'
 | 
			
		||||
  import languagesObject from '../../i18n/messages'
 | 
			
		||||
  import ISO6391 from 'iso-639-1'
 | 
			
		||||
  import _ from 'lodash'
 | 
			
		||||
 | 
			
		||||
export default {
 | 
			
		||||
  computed: {
 | 
			
		||||
    languageCodes () {
 | 
			
		||||
      return Object.keys(languagesObject)
 | 
			
		||||
    },
 | 
			
		||||
  export default {
 | 
			
		||||
    computed: {
 | 
			
		||||
      languageCodes () {
 | 
			
		||||
        return Object.keys(languagesObject)
 | 
			
		||||
      },
 | 
			
		||||
 | 
			
		||||
    languageNames () {
 | 
			
		||||
      return _.map(this.languageCodes, ISO6391.getName)
 | 
			
		||||
    },
 | 
			
		||||
      languageNames () {
 | 
			
		||||
        return _.map(this.languageCodes, ISO6391.getName)
 | 
			
		||||
      },
 | 
			
		||||
 | 
			
		||||
    language: {
 | 
			
		||||
      get: function () { return this.$store.state.config.interfaceLanguage },
 | 
			
		||||
      set: function (val) {
 | 
			
		||||
        this.$store.dispatch('setOption', { name: 'interfaceLanguage', value: val })
 | 
			
		||||
        this.$i18n.locale = val
 | 
			
		||||
      language: {
 | 
			
		||||
        get: function () { return this.$store.state.config.interfaceLanguage },
 | 
			
		||||
        set: function (val) {
 | 
			
		||||
          this.$store.dispatch('setOption', { name: 'interfaceLanguage', value: val })
 | 
			
		||||
          this.$i18n.locale = val
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
</script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,25 +1,13 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div>
 | 
			
		||||
    <a
 | 
			
		||||
      class="link-preview-card"
 | 
			
		||||
      :href="card.url"
 | 
			
		||||
      target="_blank"
 | 
			
		||||
      rel="noopener"
 | 
			
		||||
    >
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="useImage"
 | 
			
		||||
        class="card-image"
 | 
			
		||||
        :class="{ 'small-image': size === 'small' }"
 | 
			
		||||
      >
 | 
			
		||||
        <img :src="card.image">
 | 
			
		||||
    <a class="link-preview-card" :href="card.url" target="_blank" rel="noopener">
 | 
			
		||||
      <div class="card-image" :class="{ 'small-image': size === 'small' }" v-if="useImage">
 | 
			
		||||
        <img :src="card.image"></img>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="card-content">
 | 
			
		||||
        <span class="card-host faint">{{ card.provider_name }}</span>
 | 
			
		||||
        <h4 class="card-title">{{ card.title }}</h4>
 | 
			
		||||
        <p
 | 
			
		||||
          v-if="useDescription"
 | 
			
		||||
          class="card-description"
 | 
			
		||||
        >{{ card.description }}</p>
 | 
			
		||||
        <p class="card-description" v-if="useDescription">{{ card.description }}</p>
 | 
			
		||||
      </div>
 | 
			
		||||
    </a>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -39,7 +39,7 @@ const LoginForm = {
 | 
			
		|||
          }
 | 
			
		||||
          this.$store.commit('setToken', result.access_token)
 | 
			
		||||
          this.$store.dispatch('loginUser', result.access_token)
 | 
			
		||||
          this.$router.push({ name: 'friends' })
 | 
			
		||||
          this.$router.push({name: 'friends'})
 | 
			
		||||
        })
 | 
			
		||||
      })
 | 
			
		||||
    },
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -2,96 +2,42 @@
 | 
			
		|||
  <div class="login panel panel-default">
 | 
			
		||||
    <!-- Default panel contents -->
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      {{ $t('login.login') }}
 | 
			
		||||
      {{$t('login.login')}}
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="panel-body">
 | 
			
		||||
      <form
 | 
			
		||||
        v-if="loginMethod == 'password'"
 | 
			
		||||
        class="login-form"
 | 
			
		||||
        @submit.prevent="submit(user)"
 | 
			
		||||
      >
 | 
			
		||||
        <div class="form-group">
 | 
			
		||||
          <label for="username">{{ $t('login.username') }}</label>
 | 
			
		||||
          <input
 | 
			
		||||
            id="username"
 | 
			
		||||
            v-model="user.username"
 | 
			
		||||
            :disabled="loggingIn"
 | 
			
		||||
            class="form-control"
 | 
			
		||||
            :placeholder="$t('login.placeholder')"
 | 
			
		||||
          >
 | 
			
		||||
      <form v-if="loginMethod == 'password'" v-on:submit.prevent='submit(user)' class='login-form'>
 | 
			
		||||
        <div class='form-group'>
 | 
			
		||||
          <label for='username'>{{$t('login.username')}}</label>
 | 
			
		||||
          <input :disabled="loggingIn" v-model='user.username' class='form-control' id='username' v-bind:placeholder="$t('login.placeholder')">
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="form-group">
 | 
			
		||||
          <label for="password">{{ $t('login.password') }}</label>
 | 
			
		||||
          <input
 | 
			
		||||
            id="password"
 | 
			
		||||
            v-model="user.password"
 | 
			
		||||
            :disabled="loggingIn"
 | 
			
		||||
            class="form-control"
 | 
			
		||||
            type="password"
 | 
			
		||||
          >
 | 
			
		||||
        <div class='form-group'>
 | 
			
		||||
          <label for='password'>{{$t('login.password')}}</label>
 | 
			
		||||
          <input :disabled="loggingIn" v-model='user.password' class='form-control' id='password' type='password'>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="form-group">
 | 
			
		||||
          <div class="login-bottom">
 | 
			
		||||
            <div>
 | 
			
		||||
              <router-link
 | 
			
		||||
                v-if="registrationOpen"
 | 
			
		||||
                :to="{name: 'registration'}"
 | 
			
		||||
                class="register"
 | 
			
		||||
              >
 | 
			
		||||
                {{ $t('login.register') }}
 | 
			
		||||
              </router-link>
 | 
			
		||||
            </div>
 | 
			
		||||
            <button
 | 
			
		||||
              :disabled="loggingIn"
 | 
			
		||||
              type="submit"
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('login.login') }}
 | 
			
		||||
            </button>
 | 
			
		||||
        <div class='form-group'>
 | 
			
		||||
          <div class='login-bottom'>
 | 
			
		||||
            <div><router-link :to="{name: 'registration'}" v-if='registrationOpen' class='register'>{{$t('login.register')}}</router-link></div>
 | 
			
		||||
            <button :disabled="loggingIn" type='submit' class='btn btn-default'>{{$t('login.login')}}</button>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </form>
 | 
			
		||||
 | 
			
		||||
      <form
 | 
			
		||||
        v-if="loginMethod == 'token'"
 | 
			
		||||
        class="login-form"
 | 
			
		||||
        @submit.prevent="oAuthLogin"
 | 
			
		||||
      >
 | 
			
		||||
      <form v-if="loginMethod == 'token'" v-on:submit.prevent='oAuthLogin'  class="login-form">
 | 
			
		||||
        <div class="form-group">
 | 
			
		||||
          <p>{{ $t('login.description') }}</p>
 | 
			
		||||
          <p>{{$t('login.description')}}</p>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="form-group">
 | 
			
		||||
          <div class="login-bottom">
 | 
			
		||||
            <div>
 | 
			
		||||
              <router-link
 | 
			
		||||
                v-if="registrationOpen"
 | 
			
		||||
                :to="{name: 'registration'}"
 | 
			
		||||
                class="register"
 | 
			
		||||
              >
 | 
			
		||||
                {{ $t('login.register') }}
 | 
			
		||||
              </router-link>
 | 
			
		||||
            </div>
 | 
			
		||||
            <button
 | 
			
		||||
              :disabled="loggingIn"
 | 
			
		||||
              type="submit"
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('login.login') }}
 | 
			
		||||
            </button>
 | 
			
		||||
        <div class='form-group'>
 | 
			
		||||
          <div class='login-bottom'>
 | 
			
		||||
            <div><router-link :to="{name: 'registration'}" v-if='registrationOpen' class='register'>{{$t('login.register')}}</router-link></div>
 | 
			
		||||
            <button :disabled="loggingIn" type='submit' class='btn btn-default'>{{$t('login.login')}}</button>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </form>
 | 
			
		||||
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="authError"
 | 
			
		||||
        class="form-group"
 | 
			
		||||
      >
 | 
			
		||||
        <div class="alert error">
 | 
			
		||||
          {{ authError }}
 | 
			
		||||
          <i
 | 
			
		||||
            class="button-icon icon-cancel"
 | 
			
		||||
            @click="clearError"
 | 
			
		||||
          />
 | 
			
		||||
      
 | 
			
		||||
      <div v-if="authError" class='form-group'>
 | 
			
		||||
        <div class='alert error'>
 | 
			
		||||
          {{authError}}
 | 
			
		||||
          <i class="button-icon icon-cancel" @click="clearError"></i>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,33 +1,25 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    v-if="showing"
 | 
			
		||||
    class="modal-view media-modal-view"
 | 
			
		||||
    @click.prevent="hide"
 | 
			
		||||
  >
 | 
			
		||||
    <img
 | 
			
		||||
      v-if="type === 'image'"
 | 
			
		||||
      class="modal-image"
 | 
			
		||||
      :src="currentMedia.url"
 | 
			
		||||
    >
 | 
			
		||||
  <div class="modal-view media-modal-view" v-if="showing" @click.prevent="hide">
 | 
			
		||||
    <img class="modal-image" v-if="type === 'image'" :src="currentMedia.url"></img>
 | 
			
		||||
    <VideoAttachment
 | 
			
		||||
      v-if="type === 'video'"
 | 
			
		||||
      class="modal-image"
 | 
			
		||||
      v-if="type === 'video'"
 | 
			
		||||
      :attachment="currentMedia"
 | 
			
		||||
      :controls="true"
 | 
			
		||||
      @click.stop.native=""
 | 
			
		||||
    />
 | 
			
		||||
      @click.stop.native="">
 | 
			
		||||
    </VideoAttachment>
 | 
			
		||||
    <button
 | 
			
		||||
      v-if="canNavigate"
 | 
			
		||||
      :title="$t('media_modal.previous')"
 | 
			
		||||
      class="modal-view-button-arrow modal-view-button-arrow--prev"
 | 
			
		||||
      v-if="canNavigate"
 | 
			
		||||
      @click.stop.prevent="goPrev"
 | 
			
		||||
    >
 | 
			
		||||
      <i class="icon-left-open arrow-icon" />
 | 
			
		||||
    </button>
 | 
			
		||||
    <button
 | 
			
		||||
      v-if="canNavigate"
 | 
			
		||||
      :title="$t('media_modal.next')"
 | 
			
		||||
      class="modal-view-button-arrow modal-view-button-arrow--next"
 | 
			
		||||
      v-if="canNavigate"
 | 
			
		||||
      @click.stop.prevent="goNext"
 | 
			
		||||
    >
 | 
			
		||||
      <i class="icon-right-open arrow-icon" />
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -16,7 +16,7 @@ const mediaUpload = {
 | 
			
		|||
      if (file.size > store.state.instance.uploadlimit) {
 | 
			
		||||
        const filesize = fileSizeFormatService.fileSizeFormat(file.size)
 | 
			
		||||
        const allowedsize = fileSizeFormatService.fileSizeFormat(store.state.instance.uploadlimit)
 | 
			
		||||
        self.$emit('upload-failed', 'file_too_big', { filesize: filesize.num, filesizeunit: filesize.unit, allowedsize: allowedsize.num, allowedsizeunit: allowedsize.unit })
 | 
			
		||||
        self.$emit('upload-failed', 'file_too_big', {filesize: filesize.num, filesizeunit: filesize.unit, allowedsize: allowedsize.num, allowedsizeunit: allowedsize.unit})
 | 
			
		||||
        return
 | 
			
		||||
      }
 | 
			
		||||
      const formData = new FormData()
 | 
			
		||||
| 
						 | 
				
			
			@ -36,7 +36,7 @@ const mediaUpload = {
 | 
			
		|||
    },
 | 
			
		||||
    fileDrop (e) {
 | 
			
		||||
      if (e.dataTransfer.files.length > 0) {
 | 
			
		||||
        e.preventDefault() // allow dropping text like before
 | 
			
		||||
        e.preventDefault()  // allow dropping text like before
 | 
			
		||||
        this.uploadFile(e.dataTransfer.files[0])
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
| 
						 | 
				
			
			@ -54,7 +54,7 @@ const mediaUpload = {
 | 
			
		|||
        this.uploadReady = true
 | 
			
		||||
      })
 | 
			
		||||
    },
 | 
			
		||||
    change ({ target }) {
 | 
			
		||||
    change ({target}) {
 | 
			
		||||
      for (var i = 0; i < target.files.length; i++) {
 | 
			
		||||
        let file = target.files[i]
 | 
			
		||||
        this.uploadFile(file)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,29 +1,9 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="media-upload"
 | 
			
		||||
    @drop.prevent
 | 
			
		||||
    @dragover.prevent="fileDrag"
 | 
			
		||||
    @drop="fileDrop"
 | 
			
		||||
  >
 | 
			
		||||
    <label
 | 
			
		||||
      class="btn btn-default"
 | 
			
		||||
      :title="$t('tool_tip.media_upload')"
 | 
			
		||||
    >
 | 
			
		||||
      <i
 | 
			
		||||
        v-if="uploading"
 | 
			
		||||
        class="icon-spin4 animate-spin"
 | 
			
		||||
      />
 | 
			
		||||
      <i
 | 
			
		||||
        v-if="!uploading"
 | 
			
		||||
        class="icon-upload"
 | 
			
		||||
      />
 | 
			
		||||
      <input
 | 
			
		||||
        v-if="uploadReady"
 | 
			
		||||
        type="file"
 | 
			
		||||
        style="position: fixed; top: -100em"
 | 
			
		||||
        multiple="true"
 | 
			
		||||
        @change="change"
 | 
			
		||||
      >
 | 
			
		||||
  <div class="media-upload" @drop.prevent @dragover.prevent="fileDrag" @drop="fileDrop">
 | 
			
		||||
    <label class="btn btn-default" :title="$t('tool_tip.media_upload')">
 | 
			
		||||
      <i class="icon-spin4 animate-spin" v-if="uploading"></i>
 | 
			
		||||
      <i class="icon-upload" v-if="!uploading"></i>
 | 
			
		||||
      <input type="file" v-if="uploadReady" @change="change" style="position: fixed; top: -100em" multiple="true"></input>
 | 
			
		||||
    </label>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,9 +1,5 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <Timeline
 | 
			
		||||
    :title="$t('nav.mentions')"
 | 
			
		||||
    :timeline="timeline"
 | 
			
		||||
    :timeline-name="'mentions'"
 | 
			
		||||
  />
 | 
			
		||||
  <Timeline :title="$t('nav.mentions')" v-bind:timeline="timeline" v-bind:timeline-name="'mentions'"/>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./mentions.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,71 +1,34 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <nav
 | 
			
		||||
    id="nav"
 | 
			
		||||
    class="nav-bar container"
 | 
			
		||||
  >
 | 
			
		||||
    <div
 | 
			
		||||
      class="mobile-inner-nav"
 | 
			
		||||
      @click="scrollToTop()"
 | 
			
		||||
    >
 | 
			
		||||
      <div class="item">
 | 
			
		||||
        <a
 | 
			
		||||
          href="#"
 | 
			
		||||
          class="mobile-nav-button"
 | 
			
		||||
          @click.stop.prevent="toggleMobileSidebar()"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="button-icon icon-menu" />
 | 
			
		||||
  <nav class='nav-bar container' id="nav">
 | 
			
		||||
    <div class='mobile-inner-nav' @click="scrollToTop()">
 | 
			
		||||
      <div class='item'>
 | 
			
		||||
        <a href="#" class="mobile-nav-button" @click.stop.prevent="toggleMobileSidebar()">
 | 
			
		||||
          <i class="button-icon icon-menu"></i>
 | 
			
		||||
        </a>
 | 
			
		||||
        <router-link
 | 
			
		||||
          class="site-name"
 | 
			
		||||
          :to="{ name: 'root' }"
 | 
			
		||||
          active-class="home"
 | 
			
		||||
        >
 | 
			
		||||
          {{ sitename }}
 | 
			
		||||
        </router-link>
 | 
			
		||||
        <router-link class="site-name" :to="{ name: 'root' }" active-class="home">{{sitename}}</router-link>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="item right">
 | 
			
		||||
        <a
 | 
			
		||||
          v-if="currentUser"
 | 
			
		||||
          class="mobile-nav-button"
 | 
			
		||||
          href="#"
 | 
			
		||||
          @click.stop.prevent="openMobileNotifications()"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="button-icon icon-bell-alt" />
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="unseenNotificationsCount"
 | 
			
		||||
            class="alert-dot"
 | 
			
		||||
          />
 | 
			
		||||
      <div class='item right'>
 | 
			
		||||
        <a class="mobile-nav-button" v-if="currentUser" href="#" @click.stop.prevent="openMobileNotifications()">
 | 
			
		||||
          <i class="button-icon icon-bell-alt"></i>
 | 
			
		||||
          <div class="alert-dot" v-if="unseenNotificationsCount"></div>
 | 
			
		||||
        </a>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <SideDrawer
 | 
			
		||||
      ref="sideDrawer"
 | 
			
		||||
      :logout="logout"
 | 
			
		||||
    />
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="currentUser"
 | 
			
		||||
    <SideDrawer ref="sideDrawer" :logout="logout"/>
 | 
			
		||||
    <div v-if="currentUser"
 | 
			
		||||
      class="mobile-notifications-drawer"
 | 
			
		||||
      :class="{ 'closed': !notificationsOpen }"
 | 
			
		||||
      @touchstart="notificationsTouchStart"
 | 
			
		||||
      @touchmove="notificationsTouchMove"
 | 
			
		||||
    >
 | 
			
		||||
      <div class="mobile-notifications-header">
 | 
			
		||||
        <span class="title">{{ $t('notifications.notifications') }}</span>
 | 
			
		||||
        <a
 | 
			
		||||
          class="mobile-nav-button"
 | 
			
		||||
          @click.stop.prevent="closeMobileNotifications()"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="button-icon icon-cancel" />
 | 
			
		||||
        <span class="title">{{$t('notifications.notifications')}}</span>
 | 
			
		||||
        <a class="mobile-nav-button" @click.stop.prevent="closeMobileNotifications()">
 | 
			
		||||
          <i class="button-icon icon-cancel"/>
 | 
			
		||||
        </a>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="currentUser"
 | 
			
		||||
        class="mobile-notifications"
 | 
			
		||||
      >
 | 
			
		||||
        <Notifications
 | 
			
		||||
          ref="notifications"
 | 
			
		||||
          no-heading="true"
 | 
			
		||||
        />
 | 
			
		||||
      <div v-if="currentUser" class="mobile-notifications">
 | 
			
		||||
        <Notifications ref="notifications" noHeading="true"/>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <MobilePostStatusModal />
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,31 +1,23 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div v-if="currentUser">
 | 
			
		||||
    <div
 | 
			
		||||
      v-show="postFormOpen"
 | 
			
		||||
      class="post-form-modal-view modal-view"
 | 
			
		||||
      @click="closePostForm"
 | 
			
		||||
    >
 | 
			
		||||
      <div
 | 
			
		||||
        class="post-form-modal-panel panel"
 | 
			
		||||
        @click.stop=""
 | 
			
		||||
      >
 | 
			
		||||
        <div class="panel-heading">
 | 
			
		||||
          {{ $t('post_status.new_status') }}
 | 
			
		||||
        </div>
 | 
			
		||||
        <PostStatusForm
 | 
			
		||||
          class="panel-body"
 | 
			
		||||
          @posted="closePostForm"
 | 
			
		||||
        />
 | 
			
		||||
      </div>
 | 
			
		||||
<div v-if="currentUser">
 | 
			
		||||
  <div
 | 
			
		||||
    class="post-form-modal-view modal-view"
 | 
			
		||||
    v-show="postFormOpen"
 | 
			
		||||
    @click="closePostForm"
 | 
			
		||||
  >
 | 
			
		||||
    <div class="post-form-modal-panel panel" @click.stop="">
 | 
			
		||||
      <div class="panel-heading">{{$t('post_status.new_status')}}</div>
 | 
			
		||||
      <PostStatusForm class="panel-body" @posted="closePostForm"/>
 | 
			
		||||
    </div>
 | 
			
		||||
    <button
 | 
			
		||||
      class="new-status-button"
 | 
			
		||||
      :class="{ 'hidden': isHidden }"
 | 
			
		||||
      @click="openPostForm"
 | 
			
		||||
    >
 | 
			
		||||
      <i class="icon-edit" />
 | 
			
		||||
    </button>
 | 
			
		||||
  </div>
 | 
			
		||||
  <button
 | 
			
		||||
    class="new-status-button"
 | 
			
		||||
    :class="{ 'hidden': isHidden }"
 | 
			
		||||
    @click="openPostForm"
 | 
			
		||||
  >
 | 
			
		||||
    <i class="icon-edit" />
 | 
			
		||||
  </button>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./mobile_post_status_modal.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,12 +1,7 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <basic-user-card :user="user">
 | 
			
		||||
    <div class="mute-card-content-container">
 | 
			
		||||
      <button
 | 
			
		||||
        v-if="muted"
 | 
			
		||||
        class="btn btn-default"
 | 
			
		||||
        :disabled="progress"
 | 
			
		||||
        @click="unmuteUser"
 | 
			
		||||
      >
 | 
			
		||||
      <button class="btn btn-default" @click="unmuteUser" :disabled="progress" v-if="muted">
 | 
			
		||||
        <template v-if="progress">
 | 
			
		||||
          {{ $t('user_card.unmute_progress') }}
 | 
			
		||||
        </template>
 | 
			
		||||
| 
						 | 
				
			
			@ -14,12 +9,7 @@
 | 
			
		|||
          {{ $t('user_card.unmute') }}
 | 
			
		||||
        </template>
 | 
			
		||||
      </button>
 | 
			
		||||
      <button
 | 
			
		||||
        v-else
 | 
			
		||||
        class="btn btn-default"
 | 
			
		||||
        :disabled="progress"
 | 
			
		||||
        @click="muteUser"
 | 
			
		||||
      >
 | 
			
		||||
      <button class="btn btn-default" @click="muteUser" :disabled="progress" v-else>
 | 
			
		||||
        <template v-if="progress">
 | 
			
		||||
          {{ $t('user_card.mute_progress') }}
 | 
			
		||||
        </template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -2,29 +2,26 @@
 | 
			
		|||
  <div class="nav-panel">
 | 
			
		||||
    <div class="panel panel-default">
 | 
			
		||||
      <ul>
 | 
			
		||||
        <li v-if="currentUser">
 | 
			
		||||
        <li v-if='currentUser'>
 | 
			
		||||
          <router-link :to="{ name: 'friends' }">
 | 
			
		||||
            {{ $t("nav.timeline") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li v-if="currentUser">
 | 
			
		||||
        <li v-if='currentUser'>
 | 
			
		||||
          <router-link :to="{ name: 'mentions', params: { username: currentUser.screen_name } }">
 | 
			
		||||
            {{ $t("nav.mentions") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li v-if="currentUser">
 | 
			
		||||
        <li v-if='currentUser'>
 | 
			
		||||
          <router-link :to="{ name: 'dms', params: { username: currentUser.screen_name } }">
 | 
			
		||||
            {{ $t("nav.dms") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li v-if="currentUser && currentUser.locked">
 | 
			
		||||
        <li v-if='currentUser && currentUser.locked'>
 | 
			
		||||
          <router-link :to="{ name: 'friend-requests' }">
 | 
			
		||||
            {{ $t("nav.friend_requests") }}
 | 
			
		||||
            <span
 | 
			
		||||
              v-if="followRequestCount > 0"
 | 
			
		||||
              class="badge follow-request-count"
 | 
			
		||||
            >
 | 
			
		||||
              {{ followRequestCount }}
 | 
			
		||||
            {{ $t("nav.friend_requests")}}
 | 
			
		||||
            <span v-if='followRequestCount > 0' class="badge follow-request-count">
 | 
			
		||||
              {{followRequestCount}}
 | 
			
		||||
            </span>
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,90 +1,41 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <status
 | 
			
		||||
    v-if="notification.type === 'mention'"
 | 
			
		||||
    :compact="true"
 | 
			
		||||
    :statusoid="notification.status"
 | 
			
		||||
  />
 | 
			
		||||
  <div
 | 
			
		||||
    v-else
 | 
			
		||||
    class="non-mention"
 | 
			
		||||
    :class="[userClass, { highlighted: userStyle }]"
 | 
			
		||||
    :style="[ userStyle ]"
 | 
			
		||||
  >
 | 
			
		||||
    <a
 | 
			
		||||
      class="avatar-container"
 | 
			
		||||
      :href="notification.action.user.statusnet_profile_url"
 | 
			
		||||
      @click.stop.prevent.capture="toggleUserExpanded"
 | 
			
		||||
    >
 | 
			
		||||
      <UserAvatar
 | 
			
		||||
        :compact="true"
 | 
			
		||||
        :better-shadow="betterShadow"
 | 
			
		||||
        :src="notification.action.user.profile_image_url_original"
 | 
			
		||||
      />
 | 
			
		||||
  <status v-if="notification.type === 'mention'" :compact="true" :statusoid="notification.status"></status>
 | 
			
		||||
  <div class="non-mention" :class="[userClass, { highlighted: userStyle }]" :style="[ userStyle ]" v-else>
 | 
			
		||||
    <a class='avatar-container' :href="notification.action.user.statusnet_profile_url" @click.stop.prevent.capture="toggleUserExpanded">
 | 
			
		||||
      <UserAvatar :compact="true" :betterShadow="betterShadow" :src="notification.action.user.profile_image_url_original"/>
 | 
			
		||||
    </a>
 | 
			
		||||
    <div class="notification-right">
 | 
			
		||||
      <UserCard
 | 
			
		||||
        v-if="userExpanded"
 | 
			
		||||
        :user="user"
 | 
			
		||||
        :rounded="true"
 | 
			
		||||
        :bordered="true"
 | 
			
		||||
      />
 | 
			
		||||
    <div class='notification-right'>
 | 
			
		||||
      <UserCard :user="user" :rounded="true" :bordered="true" v-if="userExpanded"/>
 | 
			
		||||
      <span class="notification-details">
 | 
			
		||||
        <div class="name-and-action">
 | 
			
		||||
          <span
 | 
			
		||||
            v-if="!!notification.action.user.name_html"
 | 
			
		||||
            class="username"
 | 
			
		||||
            :title="'@'+notification.action.user.screen_name"
 | 
			
		||||
            v-html="notification.action.user.name_html"
 | 
			
		||||
          />
 | 
			
		||||
          <span
 | 
			
		||||
            v-else
 | 
			
		||||
            class="username"
 | 
			
		||||
            :title="'@'+notification.action.user.screen_name"
 | 
			
		||||
          >{{ notification.action.user.name }}</span>
 | 
			
		||||
          <span class="username" v-if="!!notification.action.user.name_html" :title="'@'+notification.action.user.screen_name" v-html="notification.action.user.name_html"></span>
 | 
			
		||||
          <span class="username" v-else :title="'@'+notification.action.user.screen_name">{{ notification.action.user.name }}</span>
 | 
			
		||||
          <span v-if="notification.type === 'like'">
 | 
			
		||||
            <i class="fa icon-star lit" />
 | 
			
		||||
            <small>{{ $t('notifications.favorited_you') }}</small>
 | 
			
		||||
            <i class="fa icon-star lit"></i>
 | 
			
		||||
            <small>{{$t('notifications.favorited_you')}}</small>
 | 
			
		||||
          </span>
 | 
			
		||||
          <span v-if="notification.type === 'repeat'">
 | 
			
		||||
            <i
 | 
			
		||||
              class="fa icon-retweet lit"
 | 
			
		||||
              :title="$t('tool_tip.repeat')"
 | 
			
		||||
            />
 | 
			
		||||
            <small>{{ $t('notifications.repeated_you') }}</small>
 | 
			
		||||
            <i class="fa icon-retweet lit" :title="$t('tool_tip.repeat')"></i>
 | 
			
		||||
            <small>{{$t('notifications.repeated_you')}}</small>
 | 
			
		||||
          </span>
 | 
			
		||||
          <span v-if="notification.type === 'follow'">
 | 
			
		||||
            <i class="fa icon-user-plus lit" />
 | 
			
		||||
            <small>{{ $t('notifications.followed_you') }}</small>
 | 
			
		||||
            <i class="fa icon-user-plus lit"></i>
 | 
			
		||||
            <small>{{$t('notifications.followed_you')}}</small>
 | 
			
		||||
          </span>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="timeago">
 | 
			
		||||
          <router-link
 | 
			
		||||
            v-if="notification.status"
 | 
			
		||||
            :to="{ name: 'conversation', params: { id: notification.status.id } }"
 | 
			
		||||
            class="faint-link"
 | 
			
		||||
          >
 | 
			
		||||
            <timeago
 | 
			
		||||
              :since="notification.action.created_at"
 | 
			
		||||
              :auto-update="240"
 | 
			
		||||
            />
 | 
			
		||||
          <router-link v-if="notification.status" :to="{ name: 'conversation', params: { id: notification.status.id } }" class="faint-link">
 | 
			
		||||
            <timeago :since="notification.action.created_at" :auto-update="240"></timeago>
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </div>
 | 
			
		||||
      </span>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="notification.type === 'follow'"
 | 
			
		||||
        class="follow-text"
 | 
			
		||||
      >
 | 
			
		||||
      <div class="follow-text" v-if="notification.type === 'follow'">
 | 
			
		||||
        <router-link :to="userProfileLink(notification.action.user)">
 | 
			
		||||
          @{{ notification.action.user.screen_name }}
 | 
			
		||||
          @{{notification.action.user.screen_name}}
 | 
			
		||||
        </router-link>
 | 
			
		||||
      </div>
 | 
			
		||||
      <template v-else>
 | 
			
		||||
        <status
 | 
			
		||||
          class="faint"
 | 
			
		||||
          :compact="true"
 | 
			
		||||
          :statusoid="notification.status"
 | 
			
		||||
          :no-heading="true"
 | 
			
		||||
        />
 | 
			
		||||
        <status class="faint" :compact="true" :statusoid="notification.status" :noHeading="true"></status>
 | 
			
		||||
      </template>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,62 +1,31 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="notifications">
 | 
			
		||||
    <div class="panel panel-default">
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="!noHeading"
 | 
			
		||||
        class="panel-heading"
 | 
			
		||||
      >
 | 
			
		||||
      <div v-if="!noHeading" class="panel-heading">
 | 
			
		||||
        <div class="title">
 | 
			
		||||
          {{ $t('notifications.notifications') }}
 | 
			
		||||
          <span
 | 
			
		||||
            v-if="unseenCount"
 | 
			
		||||
            class="badge badge-notification unseen-count"
 | 
			
		||||
          >{{ unseenCount }}</span>
 | 
			
		||||
          {{$t('notifications.notifications')}}
 | 
			
		||||
          <span class="badge badge-notification unseen-count" v-if="unseenCount">{{unseenCount}}</span>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="error"
 | 
			
		||||
          class="loadmore-error alert error"
 | 
			
		||||
          @click.prevent
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('timeline.error_fetching') }}
 | 
			
		||||
        <div @click.prevent class="loadmore-error alert error" v-if="error">
 | 
			
		||||
          {{$t('timeline.error_fetching')}}
 | 
			
		||||
        </div>
 | 
			
		||||
        <button
 | 
			
		||||
          v-if="unseenCount"
 | 
			
		||||
          class="read-button"
 | 
			
		||||
          @click.prevent="markAsSeen"
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('notifications.read') }}
 | 
			
		||||
        </button>
 | 
			
		||||
        <button v-if="unseenCount" @click.prevent="markAsSeen" class="read-button">{{$t('notifications.read')}}</button>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="panel-body">
 | 
			
		||||
        <div
 | 
			
		||||
          v-for="notification in visibleNotifications"
 | 
			
		||||
          :key="notification.action.id"
 | 
			
		||||
          class="notification"
 | 
			
		||||
          :class="{"unseen": !notification.seen}"
 | 
			
		||||
        >
 | 
			
		||||
          <div class="notification-overlay" />
 | 
			
		||||
          <notification :notification="notification" />
 | 
			
		||||
        <div v-for="notification in visibleNotifications" :key="notification.action.id" class="notification" :class='{"unseen": !notification.seen}'>
 | 
			
		||||
          <div class="notification-overlay"></div>
 | 
			
		||||
          <notification :notification="notification"></notification>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="panel-footer">
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="bottomedOut"
 | 
			
		||||
          class="new-status-notification text-center panel-footer faint"
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('notifications.no_more_notifications') }}
 | 
			
		||||
        <div v-if="bottomedOut" class="new-status-notification text-center panel-footer faint">
 | 
			
		||||
          {{$t('notifications.no_more_notifications')}}
 | 
			
		||||
        </div>
 | 
			
		||||
        <a
 | 
			
		||||
          v-else-if="!loading"
 | 
			
		||||
          href="#"
 | 
			
		||||
          @click.prevent="fetchOlderNotifications()"
 | 
			
		||||
        >
 | 
			
		||||
          <div class="new-status-notification text-center panel-footer">{{ $t('notifications.load_older') }}</div>
 | 
			
		||||
        <a v-else-if="!loading" href="#" v-on:click.prevent="fetchOlderNotifications()">
 | 
			
		||||
          <div class="new-status-notification text-center panel-footer">{{$t('notifications.load_older')}}</div>
 | 
			
		||||
        </a>
 | 
			
		||||
        <div
 | 
			
		||||
          v-else
 | 
			
		||||
          class="new-status-notification text-center panel-footer"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="icon-spin3 animate-spin" />
 | 
			
		||||
        <div v-else class="new-status-notification text-center panel-footer">
 | 
			
		||||
          <i class="icon-spin3 animate-spin"/>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -11,7 +11,7 @@ const oac = {
 | 
			
		|||
      }).then((result) => {
 | 
			
		||||
        this.$store.commit('setToken', result.access_token)
 | 
			
		||||
        this.$store.dispatch('loginUser', result.access_token)
 | 
			
		||||
        this.$router.push({ name: 'friends' })
 | 
			
		||||
        this.$router.push({name: 'friends'})
 | 
			
		||||
      })
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,39 +1,27 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="opacity-control style-control"
 | 
			
		||||
    :class="{ disabled: !present || disabled }"
 | 
			
		||||
  >
 | 
			
		||||
    <label
 | 
			
		||||
      :for="name"
 | 
			
		||||
      class="label"
 | 
			
		||||
    >
 | 
			
		||||
      {{ $t('settings.style.common.opacity') }}
 | 
			
		||||
    </label>
 | 
			
		||||
    <input
 | 
			
		||||
      v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
      :id="name + '-o'"
 | 
			
		||||
      class="opt exclude-disabled"
 | 
			
		||||
      type="checkbox"
 | 
			
		||||
      :checked="present"
 | 
			
		||||
      @input="$emit('input', !present ? fallback : undefined)"
 | 
			
		||||
    >
 | 
			
		||||
    <label
 | 
			
		||||
      v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
      class="opt-l"
 | 
			
		||||
      :for="name + '-o'"
 | 
			
		||||
    />
 | 
			
		||||
    <input
 | 
			
		||||
      :id="name"
 | 
			
		||||
      class="input-number"
 | 
			
		||||
      type="number"
 | 
			
		||||
      :value="value || fallback"
 | 
			
		||||
      :disabled="!present || disabled"
 | 
			
		||||
      max="1"
 | 
			
		||||
      min="0"
 | 
			
		||||
      step=".05"
 | 
			
		||||
      @input="$emit('input', $event.target.value)"
 | 
			
		||||
    >
 | 
			
		||||
  </div>
 | 
			
		||||
<div class="opacity-control style-control" :class="{ disabled: !present || disabled }">
 | 
			
		||||
  <label :for="name" class="label">
 | 
			
		||||
    {{$t('settings.style.common.opacity')}}
 | 
			
		||||
  </label>
 | 
			
		||||
  <input
 | 
			
		||||
    v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
    class="opt exclude-disabled"
 | 
			
		||||
    :id="name + '-o'"
 | 
			
		||||
    type="checkbox"
 | 
			
		||||
    :checked="present"
 | 
			
		||||
    @input="$emit('input', !present ? fallback : undefined)">
 | 
			
		||||
  <label v-if="typeof fallback !== 'undefined'" class="opt-l" :for="name + '-o'"></label>
 | 
			
		||||
  <input
 | 
			
		||||
    :id="name"
 | 
			
		||||
    class="input-number"
 | 
			
		||||
    type="number"
 | 
			
		||||
    :value="value || fallback"
 | 
			
		||||
    :disabled="!present || disabled"
 | 
			
		||||
    @input="$emit('input', $event.target.value)"
 | 
			
		||||
    max="1"
 | 
			
		||||
    min="0"
 | 
			
		||||
    step=".05">
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -6,13 +6,13 @@ import fileTypeService from '../../services/file_type/file_type.service.js'
 | 
			
		|||
import Completion from '../../services/completion/completion.js'
 | 
			
		||||
import { take, filter, reject, map, uniqBy } from 'lodash'
 | 
			
		||||
 | 
			
		||||
const buildMentionsString = ({ user, attentions }, currentUser) => {
 | 
			
		||||
const buildMentionsString = ({user, attentions}, currentUser) => {
 | 
			
		||||
  let allAttentions = [...attentions]
 | 
			
		||||
 | 
			
		||||
  allAttentions.unshift(user)
 | 
			
		||||
 | 
			
		||||
  allAttentions = uniqBy(allAttentions, 'id')
 | 
			
		||||
  allAttentions = reject(allAttentions, { id: currentUser.id })
 | 
			
		||||
  allAttentions = reject(allAttentions, {id: currentUser.id})
 | 
			
		||||
 | 
			
		||||
  let mentions = map(allAttentions, (attention) => {
 | 
			
		||||
    return `@${attention.screen_name}`
 | 
			
		||||
| 
						 | 
				
			
			@ -48,17 +48,17 @@ const PostStatusForm = {
 | 
			
		|||
    let statusText = preset || ''
 | 
			
		||||
 | 
			
		||||
    const scopeCopy = typeof this.$store.state.config.scopeCopy === 'undefined'
 | 
			
		||||
      ? this.$store.state.instance.scopeCopy
 | 
			
		||||
      : this.$store.state.config.scopeCopy
 | 
			
		||||
          ? this.$store.state.instance.scopeCopy
 | 
			
		||||
          : this.$store.state.config.scopeCopy
 | 
			
		||||
 | 
			
		||||
    if (this.replyTo) {
 | 
			
		||||
      const currentUser = this.$store.state.users.currentUser
 | 
			
		||||
      statusText = buildMentionsString({ user: this.repliedUser, attentions: this.attentions }, currentUser)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    const scope = ((this.copyMessageScope && scopeCopy) || this.copyMessageScope === 'direct')
 | 
			
		||||
      ? this.copyMessageScope
 | 
			
		||||
      : this.$store.state.users.currentUser.default_scope
 | 
			
		||||
    const scope = (this.copyMessageScope && scopeCopy || this.copyMessageScope === 'direct')
 | 
			
		||||
          ? this.copyMessageScope
 | 
			
		||||
          : this.$store.state.users.currentUser.default_scope
 | 
			
		||||
 | 
			
		||||
    const contentType = typeof this.$store.state.config.postContentType === 'undefined'
 | 
			
		||||
      ? this.$store.state.instance.postContentType
 | 
			
		||||
| 
						 | 
				
			
			@ -88,13 +88,13 @@ const PostStatusForm = {
 | 
			
		|||
        const query = this.textAtCaret.slice(1).toUpperCase()
 | 
			
		||||
        const matchedUsers = filter(this.users, (user) => {
 | 
			
		||||
          return user.screen_name.toUpperCase().startsWith(query) ||
 | 
			
		||||
            (user.name && user.name.toUpperCase().startsWith(query))
 | 
			
		||||
            user.name && user.name.toUpperCase().startsWith(query)
 | 
			
		||||
        })
 | 
			
		||||
        if (matchedUsers.length <= 0) {
 | 
			
		||||
          return false
 | 
			
		||||
        }
 | 
			
		||||
        // eslint-disable-next-line camelcase
 | 
			
		||||
        return map(take(matchedUsers, 5), ({ screen_name, name, profile_image_url_original }, index) => ({
 | 
			
		||||
        return map(take(matchedUsers, 5), ({screen_name, name, profile_image_url_original}, index) => ({
 | 
			
		||||
          // eslint-disable-next-line camelcase
 | 
			
		||||
          screen_name: `@${screen_name}`,
 | 
			
		||||
          name: name,
 | 
			
		||||
| 
						 | 
				
			
			@ -107,8 +107,7 @@ const PostStatusForm = {
 | 
			
		|||
        if (matchedEmoji.length <= 0) {
 | 
			
		||||
          return false
 | 
			
		||||
        }
 | 
			
		||||
        // eslint-disable-next-line camelcase
 | 
			
		||||
        return map(take(matchedEmoji, 5), ({ shortcode, image_url, utf }, index) => ({
 | 
			
		||||
        return map(take(matchedEmoji, 5), ({shortcode, image_url, utf}, index) => ({
 | 
			
		||||
          screen_name: `:${shortcode}:`,
 | 
			
		||||
          name: '',
 | 
			
		||||
          utf: utf || '',
 | 
			
		||||
| 
						 | 
				
			
			@ -135,8 +134,8 @@ const PostStatusForm = {
 | 
			
		|||
    },
 | 
			
		||||
    showAllScopes () {
 | 
			
		||||
      const minimalScopesMode = typeof this.$store.state.config.minimalScopesMode === 'undefined'
 | 
			
		||||
        ? this.$store.state.instance.minimalScopesMode
 | 
			
		||||
        : this.$store.state.config.minimalScopesMode
 | 
			
		||||
            ? this.$store.state.instance.minimalScopesMode
 | 
			
		||||
            : this.$store.state.config.minimalScopesMode
 | 
			
		||||
      return !minimalScopesMode
 | 
			
		||||
    },
 | 
			
		||||
    emoji () {
 | 
			
		||||
| 
						 | 
				
			
			@ -234,7 +233,7 @@ const PostStatusForm = {
 | 
			
		|||
    onKeydown (e) {
 | 
			
		||||
      e.stopPropagation()
 | 
			
		||||
    },
 | 
			
		||||
    setCaret ({ target: { selectionStart } }) {
 | 
			
		||||
    setCaret ({target: {selectionStart}}) {
 | 
			
		||||
      this.caret = selectionStart
 | 
			
		||||
    },
 | 
			
		||||
    postStatus (newStatus) {
 | 
			
		||||
| 
						 | 
				
			
			@ -315,7 +314,7 @@ const PostStatusForm = {
 | 
			
		|||
    },
 | 
			
		||||
    fileDrop (e) {
 | 
			
		||||
      if (e.dataTransfer.files.length > 0) {
 | 
			
		||||
        e.preventDefault() // allow dropping text like before
 | 
			
		||||
        e.preventDefault()  // allow dropping text like before
 | 
			
		||||
        this.dropFiles = e.dataTransfer.files
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,204 +1,107 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="post-status-form">
 | 
			
		||||
    <form @submit.prevent="postStatus(newStatus)">
 | 
			
		||||
      <div class="form-group">
 | 
			
		||||
        <i18n
 | 
			
		||||
          v-if="!$store.state.users.currentUser.locked && newStatus.visibility == 'private'"
 | 
			
		||||
          path="post_status.account_not_locked_warning"
 | 
			
		||||
          tag="p"
 | 
			
		||||
          class="visibility-notice"
 | 
			
		||||
        >
 | 
			
		||||
          <router-link :to="{ name: 'user-settings' }">
 | 
			
		||||
            {{ $t('post_status.account_not_locked_warning_link') }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </i18n>
 | 
			
		||||
        <p
 | 
			
		||||
          v-if="newStatus.visibility === 'direct'"
 | 
			
		||||
          class="visibility-notice"
 | 
			
		||||
        >
 | 
			
		||||
          <span v-if="safeDMEnabled">{{ $t('post_status.direct_warning_to_first_only') }}</span>
 | 
			
		||||
          <span v-else>{{ $t('post_status.direct_warning_to_all') }}</span>
 | 
			
		||||
        </p>
 | 
			
		||||
        <EmojiInput
 | 
			
		||||
          v-if="newStatus.spoilerText || alwaysShowSubject"
 | 
			
		||||
          v-model="newStatus.spoilerText"
 | 
			
		||||
          type="text"
 | 
			
		||||
          :placeholder="$t('post_status.content_warning')"
 | 
			
		||||
          classname="form-control"
 | 
			
		||||
        />
 | 
			
		||||
        <textarea
 | 
			
		||||
          ref="textarea"
 | 
			
		||||
          v-model="newStatus.status"
 | 
			
		||||
          :placeholder="$t('post_status.default')"
 | 
			
		||||
          rows="1"
 | 
			
		||||
          class="form-control"
 | 
			
		||||
          :disabled="posting"
 | 
			
		||||
          @click="setCaret"
 | 
			
		||||
          @keyup.exact="setCaret"
 | 
			
		||||
          @keydown.exact="onKeydown"
 | 
			
		||||
          @keydown.exact.down="cycleForward"
 | 
			
		||||
          @keydown.exact.up="cycleBackward"
 | 
			
		||||
          @keydown.exact.shift.tab="cycleBackward"
 | 
			
		||||
          @keydown.exact.tab="cycleForward"
 | 
			
		||||
          @keydown.exact.enter="replaceCandidate"
 | 
			
		||||
          @keydown.exact.meta.enter="postStatus(newStatus)"
 | 
			
		||||
          @keyup.exact.ctrl.enter="postStatus(newStatus)"
 | 
			
		||||
          @drop="fileDrop"
 | 
			
		||||
          @dragover.prevent="fileDrag"
 | 
			
		||||
          @input="resize"
 | 
			
		||||
          @paste="paste"
 | 
			
		||||
        />
 | 
			
		||||
        <div class="visibility-tray">
 | 
			
		||||
          <span
 | 
			
		||||
            v-if="formattingOptionsEnabled"
 | 
			
		||||
            class="text-format"
 | 
			
		||||
          >
 | 
			
		||||
            <label
 | 
			
		||||
              for="post-content-type"
 | 
			
		||||
              class="select"
 | 
			
		||||
            >
 | 
			
		||||
              <select
 | 
			
		||||
                id="post-content-type"
 | 
			
		||||
                v-model="newStatus.contentType"
 | 
			
		||||
                class="form-control"
 | 
			
		||||
              >
 | 
			
		||||
                <option
 | 
			
		||||
                  v-for="postFormat in postFormats"
 | 
			
		||||
                  :key="postFormat"
 | 
			
		||||
                  :value="postFormat"
 | 
			
		||||
                >
 | 
			
		||||
                  {{ $t(`post_status.content_type["${postFormat}"]`) }}
 | 
			
		||||
                </option>
 | 
			
		||||
              </select>
 | 
			
		||||
              <i class="icon-down-open" />
 | 
			
		||||
            </label>
 | 
			
		||||
          </span>
 | 
			
		||||
 | 
			
		||||
          <scope-selector
 | 
			
		||||
            :show-all="showAllScopes"
 | 
			
		||||
            :user-default="userDefaultScope"
 | 
			
		||||
            :original-scope="copyMessageScope"
 | 
			
		||||
            :initial-scope="newStatus.visibility"
 | 
			
		||||
            :on-scope-change="changeVis"
 | 
			
		||||
          />
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="candidates"
 | 
			
		||||
        class="autocomplete-panel"
 | 
			
		||||
<div class="post-status-form">
 | 
			
		||||
  <form @submit.prevent="postStatus(newStatus)">
 | 
			
		||||
    <div class="form-group" >
 | 
			
		||||
      <i18n
 | 
			
		||||
        v-if="!$store.state.users.currentUser.locked && newStatus.visibility == 'private'"
 | 
			
		||||
        path="post_status.account_not_locked_warning"
 | 
			
		||||
        tag="p"
 | 
			
		||||
        class="visibility-notice">
 | 
			
		||||
        <router-link :to="{ name: 'user-settings' }">{{ $t('post_status.account_not_locked_warning_link') }}</router-link>
 | 
			
		||||
      </i18n>
 | 
			
		||||
      <p v-if="newStatus.visibility === 'direct'" class="visibility-notice">
 | 
			
		||||
        <span v-if="safeDMEnabled">{{ $t('post_status.direct_warning_to_first_only') }}</span>
 | 
			
		||||
        <span v-else>{{ $t('post_status.direct_warning_to_all') }}</span>
 | 
			
		||||
      </p>
 | 
			
		||||
      <EmojiInput
 | 
			
		||||
        v-if="newStatus.spoilerText || alwaysShowSubject"
 | 
			
		||||
        type="text"
 | 
			
		||||
        :placeholder="$t('post_status.content_warning')"
 | 
			
		||||
        v-model="newStatus.spoilerText"
 | 
			
		||||
        classname="form-control"
 | 
			
		||||
      />
 | 
			
		||||
      <textarea
 | 
			
		||||
        ref="textarea"
 | 
			
		||||
        @click="setCaret"
 | 
			
		||||
        @keyup="setCaret" v-model="newStatus.status" :placeholder="$t('post_status.default')" rows="1" class="form-control"
 | 
			
		||||
        @keydown="onKeydown"
 | 
			
		||||
        @keydown.down="cycleForward"
 | 
			
		||||
        @keydown.up="cycleBackward"
 | 
			
		||||
        @keydown.shift.tab="cycleBackward"
 | 
			
		||||
        @keydown.tab="cycleForward"
 | 
			
		||||
        @keydown.enter="replaceCandidate"
 | 
			
		||||
        @keydown.meta.enter="postStatus(newStatus)"
 | 
			
		||||
        @keyup.ctrl.enter="postStatus(newStatus)"
 | 
			
		||||
        @drop="fileDrop"
 | 
			
		||||
        @dragover.prevent="fileDrag"
 | 
			
		||||
        @input="resize"
 | 
			
		||||
        @paste="paste"
 | 
			
		||||
        :disabled="posting"
 | 
			
		||||
      >
 | 
			
		||||
      </textarea>
 | 
			
		||||
      <div class="visibility-tray">
 | 
			
		||||
        <span class="text-format" v-if="formattingOptionsEnabled">
 | 
			
		||||
          <label for="post-content-type" class="select">
 | 
			
		||||
            <select id="post-content-type" v-model="newStatus.contentType" class="form-control">
 | 
			
		||||
              <option v-for="postFormat in postFormats" :key="postFormat" :value="postFormat">
 | 
			
		||||
                {{$t(`post_status.content_type["${postFormat}"]`)}}
 | 
			
		||||
              </option>
 | 
			
		||||
            </select>
 | 
			
		||||
            <i class="icon-down-open"></i>
 | 
			
		||||
          </label>
 | 
			
		||||
        </span>
 | 
			
		||||
 | 
			
		||||
        <scope-selector
 | 
			
		||||
          :showAll="showAllScopes"
 | 
			
		||||
          :userDefault="userDefaultScope"
 | 
			
		||||
          :originalScope="copyMessageScope"
 | 
			
		||||
          :initialScope="newStatus.visibility"
 | 
			
		||||
          :onScopeChange="changeVis"/>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="autocomplete-panel" v-if="candidates">
 | 
			
		||||
        <div class="autocomplete-panel-body">
 | 
			
		||||
          <div
 | 
			
		||||
            v-for="(candidate, index) in candidates"
 | 
			
		||||
            :key="index"
 | 
			
		||||
            @click="replace(candidate.utf || (candidate.screen_name + ' '))"
 | 
			
		||||
            class="autocomplete-item"
 | 
			
		||||
            :class="{ highlighted: candidate.highlighted }"
 | 
			
		||||
            @click="replace(candidate.utf || (candidate.screen_name + ' '))"
 | 
			
		||||
          >
 | 
			
		||||
            <span v-if="candidate.img"><img :src="candidate.img"></span>
 | 
			
		||||
            <span v-else>{{ candidate.utf }}</span>
 | 
			
		||||
            <span>{{ candidate.screen_name }}<small>{{ candidate.name }}</small></span>
 | 
			
		||||
            <span v-if="candidate.img"><img :src="candidate.img" /></span>
 | 
			
		||||
            <span v-else>{{candidate.utf}}</span>
 | 
			
		||||
            <span>{{candidate.screen_name}}<small>{{candidate.name}}</small></span>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="form-bottom">
 | 
			
		||||
        <media-upload
 | 
			
		||||
          ref="mediaUpload"
 | 
			
		||||
          :drop-files="dropFiles"
 | 
			
		||||
          @uploading="disableSubmit"
 | 
			
		||||
          @uploaded="addMediaFile"
 | 
			
		||||
          @upload-failed="uploadFailed"
 | 
			
		||||
        />
 | 
			
		||||
      <div class='form-bottom'>
 | 
			
		||||
        <media-upload ref="mediaUpload" @uploading="disableSubmit" @uploaded="addMediaFile" @upload-failed="uploadFailed" :drop-files="dropFiles"></media-upload>
 | 
			
		||||
 | 
			
		||||
        <p
 | 
			
		||||
          v-if="isOverLengthLimit"
 | 
			
		||||
          class="error"
 | 
			
		||||
        >
 | 
			
		||||
          {{ charactersLeft }}
 | 
			
		||||
        </p>
 | 
			
		||||
        <p
 | 
			
		||||
          v-else-if="hasStatusLengthLimit"
 | 
			
		||||
          class="faint"
 | 
			
		||||
        >
 | 
			
		||||
          {{ charactersLeft }}
 | 
			
		||||
        </p>
 | 
			
		||||
        <p v-if="isOverLengthLimit" class="error">{{ charactersLeft }}</p>
 | 
			
		||||
        <p class="faint" v-else-if="hasStatusLengthLimit">{{ charactersLeft }}</p>
 | 
			
		||||
 | 
			
		||||
        <button
 | 
			
		||||
          v-if="posting"
 | 
			
		||||
          disabled
 | 
			
		||||
          class="btn btn-default"
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('post_status.posting') }}
 | 
			
		||||
        </button>
 | 
			
		||||
        <button
 | 
			
		||||
          v-else-if="isOverLengthLimit"
 | 
			
		||||
          disabled
 | 
			
		||||
          class="btn btn-default"
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('general.submit') }}
 | 
			
		||||
        </button>
 | 
			
		||||
        <button
 | 
			
		||||
          v-else
 | 
			
		||||
          :disabled="submitDisabled"
 | 
			
		||||
          type="submit"
 | 
			
		||||
          class="btn btn-default"
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('general.submit') }}
 | 
			
		||||
        </button>
 | 
			
		||||
        <button v-if="posting" disabled class="btn btn-default">{{$t('post_status.posting')}}</button>
 | 
			
		||||
        <button v-else-if="isOverLengthLimit" disabled class="btn btn-default">{{$t('general.submit')}}</button>
 | 
			
		||||
        <button v-else :disabled="submitDisabled" type="submit" class="btn btn-default">{{$t('general.submit')}}</button>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="error"
 | 
			
		||||
        class="alert error"
 | 
			
		||||
      >
 | 
			
		||||
      <div class='alert error' v-if="error">
 | 
			
		||||
        Error: {{ error }}
 | 
			
		||||
        <i
 | 
			
		||||
          class="button-icon icon-cancel"
 | 
			
		||||
          @click="clearError"
 | 
			
		||||
        />
 | 
			
		||||
        <i class="button-icon icon-cancel" @click="clearError"></i>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="attachments">
 | 
			
		||||
        <div
 | 
			
		||||
          v-for="file in newStatus.files"
 | 
			
		||||
          :key="file.url"
 | 
			
		||||
          class="media-upload-wrapper"
 | 
			
		||||
        >
 | 
			
		||||
          <i
 | 
			
		||||
            class="fa button-icon icon-cancel"
 | 
			
		||||
            @click="removeMediaFile(file)"
 | 
			
		||||
          />
 | 
			
		||||
        <div class="media-upload-wrapper" v-for="file in newStatus.files">
 | 
			
		||||
          <i class="fa button-icon icon-cancel" @click="removeMediaFile(file)"></i>
 | 
			
		||||
          <div class="media-upload-container attachment">
 | 
			
		||||
            <img
 | 
			
		||||
              v-if="type(file) === 'image'"
 | 
			
		||||
              class="thumbnail media-upload"
 | 
			
		||||
              :src="file.url"
 | 
			
		||||
            >
 | 
			
		||||
            <video
 | 
			
		||||
              v-if="type(file) === 'video'"
 | 
			
		||||
              :src="file.url"
 | 
			
		||||
              controls
 | 
			
		||||
            />
 | 
			
		||||
            <audio
 | 
			
		||||
              v-if="type(file) === 'audio'"
 | 
			
		||||
              :src="file.url"
 | 
			
		||||
              controls
 | 
			
		||||
            />
 | 
			
		||||
            <a
 | 
			
		||||
              v-if="type(file) === 'unknown'"
 | 
			
		||||
              :href="file.url"
 | 
			
		||||
            >{{ file.url }}</a>
 | 
			
		||||
            <img class="thumbnail media-upload" :src="file.url" v-if="type(file) === 'image'"></img>
 | 
			
		||||
            <video v-if="type(file) === 'video'" :src="file.url" controls></video>
 | 
			
		||||
            <audio v-if="type(file) === 'audio'" :src="file.url" controls></audio>
 | 
			
		||||
            <a v-if="type(file) === 'unknown'" :href="file.url">{{file.url}}</a>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="newStatus.files.length > 0"
 | 
			
		||||
        class="upload_settings"
 | 
			
		||||
      >
 | 
			
		||||
        <input
 | 
			
		||||
          id="filesSensitive"
 | 
			
		||||
          v-model="newStatus.nsfw"
 | 
			
		||||
          type="checkbox"
 | 
			
		||||
        >
 | 
			
		||||
        <label for="filesSensitive">{{ $t('post_status.attachments_sensitive') }}</label>
 | 
			
		||||
      <div class="upload_settings" v-if="newStatus.files.length > 0">
 | 
			
		||||
        <input type="checkbox" id="filesSensitive" v-model="newStatus.nsfw">
 | 
			
		||||
        <label for="filesSensitive">{{$t('post_status.attachments_sensitive')}}</label>
 | 
			
		||||
      </div>
 | 
			
		||||
    </form>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			@ -311,6 +214,7 @@
 | 
			
		|||
    }
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
  .btn {
 | 
			
		||||
    cursor: pointer;
 | 
			
		||||
  }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,9 +1,5 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <Timeline
 | 
			
		||||
    :title="$t('nav.twkn')"
 | 
			
		||||
    :timeline="timeline"
 | 
			
		||||
    :timeline-name="'publicAndExternal'"
 | 
			
		||||
  />
 | 
			
		||||
  <Timeline :title="$t('nav.twkn')" v-bind:timeline="timeline" v-bind:timeline-name="'publicAndExternal'"/>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./public_and_external_timeline.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,9 +1,5 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <Timeline
 | 
			
		||||
    :title="$t('nav.public_tl')"
 | 
			
		||||
    :timeline="timeline"
 | 
			
		||||
    :timeline-name="'public'"
 | 
			
		||||
  />
 | 
			
		||||
  <Timeline :title="$t('nav.public_tl')" v-bind:timeline="timeline" v-bind:timeline-name="'public'"/>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./public_timeline.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,50 +1,37 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="range-control style-control"
 | 
			
		||||
    :class="{ disabled: !present || disabled }"
 | 
			
		||||
  >
 | 
			
		||||
    <label
 | 
			
		||||
      :for="name"
 | 
			
		||||
      class="label"
 | 
			
		||||
    >
 | 
			
		||||
      {{ label }}
 | 
			
		||||
    </label>
 | 
			
		||||
    <input
 | 
			
		||||
      v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
      :id="name + '-o'"
 | 
			
		||||
      class="opt exclude-disabled"
 | 
			
		||||
      type="checkbox"
 | 
			
		||||
      :checked="present"
 | 
			
		||||
      @input="$emit('input', !present ? fallback : undefined)"
 | 
			
		||||
    >
 | 
			
		||||
    <label
 | 
			
		||||
      v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
      class="opt-l"
 | 
			
		||||
      :for="name + '-o'"
 | 
			
		||||
    />
 | 
			
		||||
    <input
 | 
			
		||||
      :id="name"
 | 
			
		||||
      class="input-number"
 | 
			
		||||
      type="range"
 | 
			
		||||
      :value="value || fallback"
 | 
			
		||||
      :disabled="!present || disabled"
 | 
			
		||||
      :max="max || hardMax || 100"
 | 
			
		||||
      :min="min || hardMin || 0"
 | 
			
		||||
      :step="step || 1"
 | 
			
		||||
      @input="$emit('input', $event.target.value)"
 | 
			
		||||
    >
 | 
			
		||||
    <input
 | 
			
		||||
      :id="name"
 | 
			
		||||
      class="input-number"
 | 
			
		||||
      type="number"
 | 
			
		||||
      :value="value || fallback"
 | 
			
		||||
      :disabled="!present || disabled"
 | 
			
		||||
      :max="hardMax"
 | 
			
		||||
      :min="hardMin"
 | 
			
		||||
      :step="step || 1"
 | 
			
		||||
      @input="$emit('input', $event.target.value)"
 | 
			
		||||
    >
 | 
			
		||||
  </div>
 | 
			
		||||
<div class="range-control style-control" :class="{ disabled: !present || disabled }">
 | 
			
		||||
  <label :for="name" class="label">
 | 
			
		||||
    {{label}}
 | 
			
		||||
  </label>
 | 
			
		||||
  <input
 | 
			
		||||
    v-if="typeof fallback !== 'undefined'"
 | 
			
		||||
    class="opt exclude-disabled"
 | 
			
		||||
    :id="name + '-o'"
 | 
			
		||||
    type="checkbox"
 | 
			
		||||
    :checked="present"
 | 
			
		||||
    @input="$emit('input', !present ? fallback : undefined)">
 | 
			
		||||
  <label v-if="typeof fallback !== 'undefined'" class="opt-l" :for="name + '-o'"></label>
 | 
			
		||||
  <input
 | 
			
		||||
    :id="name"
 | 
			
		||||
    class="input-number"
 | 
			
		||||
    type="range"
 | 
			
		||||
    :value="value || fallback"
 | 
			
		||||
    :disabled="!present || disabled"
 | 
			
		||||
    @input="$emit('input', $event.target.value)"
 | 
			
		||||
    :max="max || hardMax || 100"
 | 
			
		||||
    :min="min || hardMin || 0"
 | 
			
		||||
    :step="step || 1">
 | 
			
		||||
  <input
 | 
			
		||||
    :id="name"
 | 
			
		||||
    class="input-number"
 | 
			
		||||
    type="number"
 | 
			
		||||
    :value="value || fallback"
 | 
			
		||||
    :disabled="!present || disabled"
 | 
			
		||||
    @input="$emit('input', $event.target.value)"
 | 
			
		||||
    :max="hardMax"
 | 
			
		||||
    :min="hardMin"
 | 
			
		||||
    :step="step || 1">
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -28,7 +28,7 @@ const registration = {
 | 
			
		|||
  },
 | 
			
		||||
  created () {
 | 
			
		||||
    if ((!this.registrationOpen && !this.token) || this.signedIn) {
 | 
			
		||||
      this.$router.push({ name: 'root' })
 | 
			
		||||
      this.$router.push({name: 'root'})
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    this.setCaptcha()
 | 
			
		||||
| 
						 | 
				
			
			@ -61,7 +61,7 @@ const registration = {
 | 
			
		|||
      if (!this.$v.$invalid) {
 | 
			
		||||
        try {
 | 
			
		||||
          await this.signUp(this.user)
 | 
			
		||||
          this.$router.push({ name: 'friends' })
 | 
			
		||||
          this.$router.push({name: 'friends'})
 | 
			
		||||
        } catch (error) {
 | 
			
		||||
          console.warn('Registration failed: ' + error)
 | 
			
		||||
        }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,234 +1,109 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="settings panel panel-default">
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      {{ $t('registration.registration') }}
 | 
			
		||||
      {{$t('registration.registration')}}
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="panel-body">
 | 
			
		||||
      <form
 | 
			
		||||
        class="registration-form"
 | 
			
		||||
        @submit.prevent="submit(user)"
 | 
			
		||||
      >
 | 
			
		||||
        <div class="container">
 | 
			
		||||
          <div class="text-fields">
 | 
			
		||||
            <div
 | 
			
		||||
              class="form-group"
 | 
			
		||||
              :class="{ 'form-group--error': $v.user.username.$error }"
 | 
			
		||||
            >
 | 
			
		||||
              <label
 | 
			
		||||
                class="form--label"
 | 
			
		||||
                for="sign-up-username"
 | 
			
		||||
              >{{ $t('login.username') }}</label>
 | 
			
		||||
              <input
 | 
			
		||||
                id="sign-up-username"
 | 
			
		||||
                v-model.trim="$v.user.username.$model"
 | 
			
		||||
                :disabled="isPending"
 | 
			
		||||
                class="form-control"
 | 
			
		||||
                :placeholder="$t('registration.username_placeholder')"
 | 
			
		||||
              >
 | 
			
		||||
      <form v-on:submit.prevent='submit(user)' class='registration-form'>
 | 
			
		||||
        <div class='container'>
 | 
			
		||||
          <div class='text-fields'>
 | 
			
		||||
            <div class='form-group' :class="{ 'form-group--error': $v.user.username.$error }">
 | 
			
		||||
              <label class='form--label' for='sign-up-username'>{{$t('login.username')}}</label>
 | 
			
		||||
              <input :disabled="isPending" v-model.trim='$v.user.username.$model' class='form-control' id='sign-up-username' :placeholder="$t('registration.username_placeholder')">
 | 
			
		||||
            </div>
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="$v.user.username.$dirty"
 | 
			
		||||
              class="form-error"
 | 
			
		||||
            >
 | 
			
		||||
            <div class="form-error" v-if="$v.user.username.$dirty">
 | 
			
		||||
              <ul>
 | 
			
		||||
                <li v-if="!$v.user.username.required">
 | 
			
		||||
                  <span>{{ $t('registration.validations.username_required') }}</span>
 | 
			
		||||
                  <span>{{$t('registration.validations.username_required')}}</span>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div
 | 
			
		||||
              class="form-group"
 | 
			
		||||
              :class="{ 'form-group--error': $v.user.fullname.$error }"
 | 
			
		||||
            >
 | 
			
		||||
              <label
 | 
			
		||||
                class="form--label"
 | 
			
		||||
                for="sign-up-fullname"
 | 
			
		||||
              >{{ $t('registration.fullname') }}</label>
 | 
			
		||||
              <input
 | 
			
		||||
                id="sign-up-fullname"
 | 
			
		||||
                v-model.trim="$v.user.fullname.$model"
 | 
			
		||||
                :disabled="isPending"
 | 
			
		||||
                class="form-control"
 | 
			
		||||
                :placeholder="$t('registration.fullname_placeholder')"
 | 
			
		||||
              >
 | 
			
		||||
            <div class='form-group' :class="{ 'form-group--error': $v.user.fullname.$error }">
 | 
			
		||||
              <label class='form--label' for='sign-up-fullname'>{{$t('registration.fullname')}}</label>
 | 
			
		||||
              <input :disabled="isPending" v-model.trim='$v.user.fullname.$model' class='form-control' id='sign-up-fullname' :placeholder="$t('registration.fullname_placeholder')">
 | 
			
		||||
            </div>
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="$v.user.fullname.$dirty"
 | 
			
		||||
              class="form-error"
 | 
			
		||||
            >
 | 
			
		||||
            <div class="form-error" v-if="$v.user.fullname.$dirty">
 | 
			
		||||
              <ul>
 | 
			
		||||
                <li v-if="!$v.user.fullname.required">
 | 
			
		||||
                  <span>{{ $t('registration.validations.fullname_required') }}</span>
 | 
			
		||||
                  <span>{{$t('registration.validations.fullname_required')}}</span>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div
 | 
			
		||||
              class="form-group"
 | 
			
		||||
              :class="{ 'form-group--error': $v.user.email.$error }"
 | 
			
		||||
            >
 | 
			
		||||
              <label
 | 
			
		||||
                class="form--label"
 | 
			
		||||
                for="email"
 | 
			
		||||
              >{{ $t('registration.email') }}</label>
 | 
			
		||||
              <input
 | 
			
		||||
                id="email"
 | 
			
		||||
                v-model="$v.user.email.$model"
 | 
			
		||||
                :disabled="isPending"
 | 
			
		||||
                class="form-control"
 | 
			
		||||
                type="email"
 | 
			
		||||
              >
 | 
			
		||||
            <div class='form-group' :class="{ 'form-group--error': $v.user.email.$error }">
 | 
			
		||||
              <label class='form--label' for='email'>{{$t('registration.email')}}</label>
 | 
			
		||||
              <input :disabled="isPending" v-model='$v.user.email.$model' class='form-control' id='email' type="email">
 | 
			
		||||
            </div>
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="$v.user.email.$dirty"
 | 
			
		||||
              class="form-error"
 | 
			
		||||
            >
 | 
			
		||||
            <div class="form-error" v-if="$v.user.email.$dirty">
 | 
			
		||||
              <ul>
 | 
			
		||||
                <li v-if="!$v.user.email.required">
 | 
			
		||||
                  <span>{{ $t('registration.validations.email_required') }}</span>
 | 
			
		||||
                  <span>{{$t('registration.validations.email_required')}}</span>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div class="form-group">
 | 
			
		||||
              <label
 | 
			
		||||
                class="form--label"
 | 
			
		||||
                for="bio"
 | 
			
		||||
              >{{ $t('registration.bio') }} ({{ $t('general.optional') }})</label>
 | 
			
		||||
              <textarea
 | 
			
		||||
                id="bio"
 | 
			
		||||
                v-model="user.bio"
 | 
			
		||||
                :disabled="isPending"
 | 
			
		||||
                class="form-control"
 | 
			
		||||
                :placeholder="bioPlaceholder"
 | 
			
		||||
              />
 | 
			
		||||
            <div class='form-group'>
 | 
			
		||||
              <label class='form--label' for='bio'>{{$t('registration.bio')}} ({{$t('general.optional')}})</label>
 | 
			
		||||
              <textarea :disabled="isPending" v-model='user.bio' class='form-control' id='bio' :placeholder="bioPlaceholder"></textarea>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div
 | 
			
		||||
              class="form-group"
 | 
			
		||||
              :class="{ 'form-group--error': $v.user.password.$error }"
 | 
			
		||||
            >
 | 
			
		||||
              <label
 | 
			
		||||
                class="form--label"
 | 
			
		||||
                for="sign-up-password"
 | 
			
		||||
              >{{ $t('login.password') }}</label>
 | 
			
		||||
              <input
 | 
			
		||||
                id="sign-up-password"
 | 
			
		||||
                v-model="user.password"
 | 
			
		||||
                :disabled="isPending"
 | 
			
		||||
                class="form-control"
 | 
			
		||||
                type="password"
 | 
			
		||||
              >
 | 
			
		||||
            <div class='form-group' :class="{ 'form-group--error': $v.user.password.$error }">
 | 
			
		||||
              <label class='form--label' for='sign-up-password'>{{$t('login.password')}}</label>
 | 
			
		||||
              <input :disabled="isPending" v-model='user.password' class='form-control' id='sign-up-password' type='password'>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="$v.user.password.$dirty"
 | 
			
		||||
              class="form-error"
 | 
			
		||||
            >
 | 
			
		||||
            <div class="form-error" v-if="$v.user.password.$dirty">
 | 
			
		||||
              <ul>
 | 
			
		||||
                <li v-if="!$v.user.password.required">
 | 
			
		||||
                  <span>{{ $t('registration.validations.password_required') }}</span>
 | 
			
		||||
                  <span>{{$t('registration.validations.password_required')}}</span>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div
 | 
			
		||||
              class="form-group"
 | 
			
		||||
              :class="{ 'form-group--error': $v.user.confirm.$error }"
 | 
			
		||||
            >
 | 
			
		||||
              <label
 | 
			
		||||
                class="form--label"
 | 
			
		||||
                for="sign-up-password-confirmation"
 | 
			
		||||
              >{{ $t('registration.password_confirm') }}</label>
 | 
			
		||||
              <input
 | 
			
		||||
                id="sign-up-password-confirmation"
 | 
			
		||||
                v-model="user.confirm"
 | 
			
		||||
                :disabled="isPending"
 | 
			
		||||
                class="form-control"
 | 
			
		||||
                type="password"
 | 
			
		||||
              >
 | 
			
		||||
            <div class='form-group' :class="{ 'form-group--error': $v.user.confirm.$error }">
 | 
			
		||||
              <label class='form--label' for='sign-up-password-confirmation'>{{$t('registration.password_confirm')}}</label>
 | 
			
		||||
              <input :disabled="isPending" v-model='user.confirm' class='form-control' id='sign-up-password-confirmation' type='password'>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="$v.user.confirm.$dirty"
 | 
			
		||||
              class="form-error"
 | 
			
		||||
            >
 | 
			
		||||
            <div class="form-error" v-if="$v.user.confirm.$dirty">
 | 
			
		||||
              <ul>
 | 
			
		||||
                <li v-if="!$v.user.confirm.required">
 | 
			
		||||
                  <span>{{ $t('registration.validations.password_confirmation_required') }}</span>
 | 
			
		||||
                  <span>{{$t('registration.validations.password_confirmation_required')}}</span>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li v-if="!$v.user.confirm.sameAsPassword">
 | 
			
		||||
                  <span>{{ $t('registration.validations.password_confirmation_match') }}</span>
 | 
			
		||||
                  <span>{{$t('registration.validations.password_confirmation_match')}}</span>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="captcha.type != 'none'"
 | 
			
		||||
              id="captcha-group"
 | 
			
		||||
              class="form-group"
 | 
			
		||||
            >
 | 
			
		||||
              <label
 | 
			
		||||
                class="form--label"
 | 
			
		||||
                for="captcha-label"
 | 
			
		||||
              >{{ $t('captcha') }}</label>
 | 
			
		||||
            <div class="form-group" id="captcha-group" v-if="captcha.type != 'none'">
 | 
			
		||||
              <label class='form--label' for='captcha-label'>{{$t('captcha')}}</label>
 | 
			
		||||
 | 
			
		||||
              <template v-if="captcha.type == 'kocaptcha'">
 | 
			
		||||
                <img
 | 
			
		||||
                  :src="captcha.url"
 | 
			
		||||
                  @click="setCaptcha"
 | 
			
		||||
                >
 | 
			
		||||
                <img v-bind:src="captcha.url" v-on:click="setCaptcha">
 | 
			
		||||
 | 
			
		||||
                <sub>{{ $t('registration.new_captcha') }}</sub>
 | 
			
		||||
                <sub>{{$t('registration.new_captcha')}}</sub>
 | 
			
		||||
 | 
			
		||||
                <input
 | 
			
		||||
                  id="captcha-answer"
 | 
			
		||||
                  v-model="captcha.solution"
 | 
			
		||||
                  :disabled="isPending"
 | 
			
		||||
                  class="form-control"
 | 
			
		||||
                  type="text"
 | 
			
		||||
                  autocomplete="off"
 | 
			
		||||
                >
 | 
			
		||||
                <input :disabled="isPending"
 | 
			
		||||
                  v-model='captcha.solution'
 | 
			
		||||
                  class='form-control' id='captcha-answer' type='text' autocomplete="off">
 | 
			
		||||
              </template>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="token"
 | 
			
		||||
              class="form-group"
 | 
			
		||||
            >
 | 
			
		||||
              <label for="token">{{ $t('registration.token') }}</label>
 | 
			
		||||
              <input
 | 
			
		||||
                id="token"
 | 
			
		||||
                v-model="token"
 | 
			
		||||
                disabled="true"
 | 
			
		||||
                class="form-control"
 | 
			
		||||
                type="text"
 | 
			
		||||
              >
 | 
			
		||||
            <div class='form-group' v-if='token' >
 | 
			
		||||
              <label for='token'>{{$t('registration.token')}}</label>
 | 
			
		||||
              <input disabled='true' v-model='token' class='form-control' id='token' type='text'>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="form-group">
 | 
			
		||||
              <button
 | 
			
		||||
                :disabled="isPending"
 | 
			
		||||
                type="submit"
 | 
			
		||||
                class="btn btn-default"
 | 
			
		||||
              >
 | 
			
		||||
                {{ $t('general.submit') }}
 | 
			
		||||
              </button>
 | 
			
		||||
            <div class='form-group'>
 | 
			
		||||
              <button :disabled="isPending" type='submit' class='btn btn-default'>{{$t('general.submit')}}</button>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div
 | 
			
		||||
            class="terms-of-service"
 | 
			
		||||
            v-html="termsOfService"
 | 
			
		||||
          />
 | 
			
		||||
          <div class='terms-of-service' v-html="termsOfService">
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="serverValidationErrors.length"
 | 
			
		||||
          class="form-group"
 | 
			
		||||
        >
 | 
			
		||||
          <div class="alert error">
 | 
			
		||||
            <span
 | 
			
		||||
              v-for="error in serverValidationErrors"
 | 
			
		||||
              :key="error"
 | 
			
		||||
            >{{ error }}</span>
 | 
			
		||||
        <div v-if="serverValidationErrors.length" class='form-group'>
 | 
			
		||||
          <div class='alert error'>
 | 
			
		||||
            <span v-for="error in serverValidationErrors">{{error}}</span>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </form>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,23 +1,9 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="remote-follow">
 | 
			
		||||
    <form
 | 
			
		||||
      method="POST"
 | 
			
		||||
      :action="subscribeUrl"
 | 
			
		||||
    >
 | 
			
		||||
      <input
 | 
			
		||||
        type="hidden"
 | 
			
		||||
        name="nickname"
 | 
			
		||||
        :value="user.screen_name"
 | 
			
		||||
      >
 | 
			
		||||
      <input
 | 
			
		||||
        type="hidden"
 | 
			
		||||
        name="profile"
 | 
			
		||||
        value=""
 | 
			
		||||
      >
 | 
			
		||||
      <button
 | 
			
		||||
        click="submit"
 | 
			
		||||
        class="remote-button"
 | 
			
		||||
      >
 | 
			
		||||
    <form method="POST" :action='subscribeUrl'>
 | 
			
		||||
      <input type="hidden" name="nickname" :value="user.screen_name">
 | 
			
		||||
      <input type="hidden" name="profile" value="">
 | 
			
		||||
      <button click="submit" class="remote-button">
 | 
			
		||||
        {{ $t('user_card.remote_follow') }}
 | 
			
		||||
      </button>
 | 
			
		||||
    </form>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -11,9 +11,9 @@ const RetweetButton = {
 | 
			
		|||
  methods: {
 | 
			
		||||
    retweet () {
 | 
			
		||||
      if (!this.status.repeated) {
 | 
			
		||||
        this.$store.dispatch('retweet', { id: this.status.id })
 | 
			
		||||
        this.$store.dispatch('retweet', {id: this.status.id})
 | 
			
		||||
      } else {
 | 
			
		||||
        this.$store.dispatch('unretweet', { id: this.status.id })
 | 
			
		||||
        this.$store.dispatch('unretweet', {id: this.status.id})
 | 
			
		||||
      }
 | 
			
		||||
      this.animated = true
 | 
			
		||||
      setTimeout(() => {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,29 +1,16 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div v-if="loggedIn">
 | 
			
		||||
    <template v-if="visibility !== 'private' && visibility !== 'direct'">
 | 
			
		||||
      <i
 | 
			
		||||
        :class="classes"
 | 
			
		||||
        class="button-icon retweet-button icon-retweet rt-active"
 | 
			
		||||
        :title="$t('tool_tip.repeat')"
 | 
			
		||||
        @click.prevent="retweet()"
 | 
			
		||||
      />
 | 
			
		||||
      <span v-if="!hidePostStatsLocal && status.repeat_num > 0">{{ status.repeat_num }}</span>
 | 
			
		||||
      <i :class='classes' class='button-icon retweet-button icon-retweet rt-active' v-on:click.prevent='retweet()' :title="$t('tool_tip.repeat')"></i>
 | 
			
		||||
      <span v-if='!hidePostStatsLocal && status.repeat_num > 0'>{{status.repeat_num}}</span>
 | 
			
		||||
    </template>
 | 
			
		||||
    <template v-else>
 | 
			
		||||
      <i
 | 
			
		||||
        :class="classes"
 | 
			
		||||
        class="button-icon icon-lock"
 | 
			
		||||
        :title="$t('timeline.no_retweet_hint')"
 | 
			
		||||
      />
 | 
			
		||||
      <i :class='classes' class='button-icon icon-lock' :title="$t('timeline.no_retweet_hint')"></i>
 | 
			
		||||
    </template>
 | 
			
		||||
  </div>
 | 
			
		||||
  <div v-else-if="!loggedIn">
 | 
			
		||||
    <i
 | 
			
		||||
      :class="classes"
 | 
			
		||||
      class="button-icon icon-retweet"
 | 
			
		||||
      :title="$t('tool_tip.repeat')"
 | 
			
		||||
    />
 | 
			
		||||
    <span v-if="!hidePostStatsLocal && status.repeat_num > 0">{{ status.repeat_num }}</span>
 | 
			
		||||
    <i :class='classes' class='button-icon icon-retweet' :title="$t('tool_tip.repeat')"></i>
 | 
			
		||||
    <span v-if='!hidePostStatsLocal && status.repeat_num > 0'>{{status.repeat_num}}</span>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -29,10 +29,10 @@ const ScopeSelector = {
 | 
			
		|||
    },
 | 
			
		||||
    css () {
 | 
			
		||||
      return {
 | 
			
		||||
        public: { selected: this.currentScope === 'public' },
 | 
			
		||||
        unlisted: { selected: this.currentScope === 'unlisted' },
 | 
			
		||||
        private: { selected: this.currentScope === 'private' },
 | 
			
		||||
        direct: { selected: this.currentScope === 'direct' }
 | 
			
		||||
        public: {selected: this.currentScope === 'public'},
 | 
			
		||||
        unlisted: {selected: this.currentScope === 'unlisted'},
 | 
			
		||||
        private: {selected: this.currentScope === 'private'},
 | 
			
		||||
        direct: {selected: this.currentScope === 'direct'}
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,34 +1,30 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div v-if="!showNothing">
 | 
			
		||||
    <i
 | 
			
		||||
      v-if="showDirect"
 | 
			
		||||
      class="icon-mail-alt"
 | 
			
		||||
      :class="css.direct"
 | 
			
		||||
      :title="$t('post_status.scope.direct')"
 | 
			
		||||
      @click="changeVis('direct')"
 | 
			
		||||
    />
 | 
			
		||||
    <i
 | 
			
		||||
      v-if="showPrivate"
 | 
			
		||||
      class="icon-lock"
 | 
			
		||||
      :class="css.private"
 | 
			
		||||
      :title="$t('post_status.scope.private')"
 | 
			
		||||
      @click="changeVis('private')"
 | 
			
		||||
    />
 | 
			
		||||
    <i
 | 
			
		||||
      v-if="showUnlisted"
 | 
			
		||||
      class="icon-lock-open-alt"
 | 
			
		||||
      :class="css.unlisted"
 | 
			
		||||
      :title="$t('post_status.scope.unlisted')"
 | 
			
		||||
      @click="changeVis('unlisted')"
 | 
			
		||||
    />
 | 
			
		||||
    <i
 | 
			
		||||
      v-if="showPublic"
 | 
			
		||||
      class="icon-globe"
 | 
			
		||||
      :class="css.public"
 | 
			
		||||
      :title="$t('post_status.scope.public')"
 | 
			
		||||
      @click="changeVis('public')"
 | 
			
		||||
    />
 | 
			
		||||
  </div>
 | 
			
		||||
<div v-if="!showNothing">
 | 
			
		||||
  <i class="icon-mail-alt"
 | 
			
		||||
     :class="css.direct"
 | 
			
		||||
     :title="$t('post_status.scope.direct')"
 | 
			
		||||
     v-if="showDirect"
 | 
			
		||||
     @click="changeVis('direct')">
 | 
			
		||||
  </i>
 | 
			
		||||
  <i class="icon-lock"
 | 
			
		||||
     :class="css.private"
 | 
			
		||||
     :title="$t('post_status.scope.private')"
 | 
			
		||||
     v-if="showPrivate"
 | 
			
		||||
     v-on:click="changeVis('private')">
 | 
			
		||||
  </i>
 | 
			
		||||
  <i class="icon-lock-open-alt"
 | 
			
		||||
     :class="css.unlisted"
 | 
			
		||||
     :title="$t('post_status.scope.unlisted')"
 | 
			
		||||
     v-if="showUnlisted"
 | 
			
		||||
     @click="changeVis('unlisted')">
 | 
			
		||||
  </i>
 | 
			
		||||
  <i class="icon-globe"
 | 
			
		||||
     :class="css.public"
 | 
			
		||||
     :title="$t('post_status.scope.public')"
 | 
			
		||||
     v-if="showPublic"
 | 
			
		||||
     @click="changeVis('public')">
 | 
			
		||||
  </i>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./scope_selector.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,476 +1,302 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="settings panel panel-default">
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      <div class="title">
 | 
			
		||||
        {{ $t('settings.settings') }}
 | 
			
		||||
<div class="settings panel panel-default">
 | 
			
		||||
  <div class="panel-heading">
 | 
			
		||||
    <div class="title">
 | 
			
		||||
      {{$t('settings.settings')}}
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <transition name="fade">
 | 
			
		||||
      <template v-if="currentSaveStateNotice">
 | 
			
		||||
        <div @click.prevent class="alert error" v-if="currentSaveStateNotice.error">
 | 
			
		||||
          {{ $t('settings.saving_err') }}
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div @click.prevent class="alert transparent" v-if="!currentSaveStateNotice.error">
 | 
			
		||||
          {{ $t('settings.saving_ok') }}
 | 
			
		||||
        </div>
 | 
			
		||||
      </template>
 | 
			
		||||
    </transition>
 | 
			
		||||
  </div>
 | 
			
		||||
  <div class="panel-body">
 | 
			
		||||
<keep-alive>
 | 
			
		||||
    <tab-switcher>
 | 
			
		||||
      <div :label="$t('settings.general')" >
 | 
			
		||||
        <div class="setting-item">
 | 
			
		||||
          <h2>{{ $t('settings.interface') }}</h2>
 | 
			
		||||
          <ul class="setting-list">
 | 
			
		||||
            <li>
 | 
			
		||||
              <interface-language-switcher />
 | 
			
		||||
            </li>
 | 
			
		||||
            <li v-if="instanceSpecificPanelPresent">
 | 
			
		||||
              <input type="checkbox" id="hideISP" v-model="hideISPLocal">
 | 
			
		||||
              <label for="hideISP">{{$t('settings.hide_isp')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
          </ul>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="setting-item">
 | 
			
		||||
          <h2>{{$t('nav.timeline')}}</h2>
 | 
			
		||||
          <ul class="setting-list">
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="hideMutedPosts" v-model="hideMutedPostsLocal">
 | 
			
		||||
              <label for="hideMutedPosts">{{$t('settings.hide_muted_posts')}} {{$t('settings.instance_default', { value: hideMutedPostsDefault })}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="collapseMessageWithSubject" v-model="collapseMessageWithSubjectLocal">
 | 
			
		||||
              <label for="collapseMessageWithSubject">
 | 
			
		||||
                {{$t('settings.collapse_subject')}} {{$t('settings.instance_default', { value: collapseMessageWithSubjectDefault })}}
 | 
			
		||||
              </label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="streaming" v-model="streamingLocal">
 | 
			
		||||
              <label for="streaming">{{$t('settings.streaming')}}</label>
 | 
			
		||||
              <ul class="setting-list suboptions" :class="[{disabled: !streamingLocal}]">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input :disabled="!streamingLocal" type="checkbox" id="pauseOnUnfocused" v-model="pauseOnUnfocusedLocal">
 | 
			
		||||
                  <label for="pauseOnUnfocused">{{$t('settings.pause_on_unfocused')}}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="autoload" v-model="autoLoadLocal">
 | 
			
		||||
              <label for="autoload">{{$t('settings.autoload')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="hoverPreview" v-model="hoverPreviewLocal">
 | 
			
		||||
              <label for="hoverPreview">{{$t('settings.reply_link_preview')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
          </ul>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div class="setting-item">
 | 
			
		||||
          <h2>{{$t('settings.composing')}}</h2>
 | 
			
		||||
          <ul class="setting-list">
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="scopeCopy" v-model="scopeCopyLocal">
 | 
			
		||||
              <label for="scopeCopy">
 | 
			
		||||
                {{$t('settings.scope_copy')}} {{$t('settings.instance_default', { value: scopeCopyDefault })}}
 | 
			
		||||
              </label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="subjectHide" v-model="alwaysShowSubjectInputLocal">
 | 
			
		||||
              <label for="subjectHide">
 | 
			
		||||
                {{$t('settings.subject_input_always_show')}} {{$t('settings.instance_default', { value: alwaysShowSubjectInputDefault })}}
 | 
			
		||||
              </label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <div>
 | 
			
		||||
                {{$t('settings.subject_line_behavior')}}
 | 
			
		||||
                <label for="subjectLineBehavior" class="select">
 | 
			
		||||
                  <select id="subjectLineBehavior" v-model="subjectLineBehaviorLocal">
 | 
			
		||||
                    <option value="email">
 | 
			
		||||
                      {{$t('settings.subject_line_email')}}
 | 
			
		||||
                      {{subjectLineBehaviorDefault == 'email' ? $t('settings.instance_default_simple') : ''}}
 | 
			
		||||
                    </option>
 | 
			
		||||
                    <option value="masto">
 | 
			
		||||
                      {{$t('settings.subject_line_mastodon')}}
 | 
			
		||||
                      {{subjectLineBehaviorDefault == 'mastodon' ? $t('settings.instance_default_simple') : ''}}
 | 
			
		||||
                    </option>
 | 
			
		||||
                    <option value="noop">
 | 
			
		||||
                      {{$t('settings.subject_line_noop')}}
 | 
			
		||||
                      {{subjectLineBehaviorDefault == 'noop' ? $t('settings.instance_default_simple') : ''}}
 | 
			
		||||
                    </option>
 | 
			
		||||
                  </select>
 | 
			
		||||
                  <i class="icon-down-open"/>
 | 
			
		||||
                </label>
 | 
			
		||||
              </div>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <div>
 | 
			
		||||
                {{$t('settings.post_status_content_type')}}
 | 
			
		||||
                <label for="postContentType" class="select">
 | 
			
		||||
                  <select id="postContentType" v-model="postContentTypeLocal">
 | 
			
		||||
                    <option v-for="postFormat in postFormats" :key="postFormat" :value="postFormat">
 | 
			
		||||
                      {{$t(`post_status.content_type["${postFormat}"]`)}}
 | 
			
		||||
                      {{postContentTypeDefault === postFormat ? $t('settings.instance_default_simple') : ''}}
 | 
			
		||||
                    </option>
 | 
			
		||||
                  </select>
 | 
			
		||||
                  <i class="icon-down-open"/>
 | 
			
		||||
                </label>
 | 
			
		||||
              </div>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="minimalScopesMode" v-model="minimalScopesModeLocal">
 | 
			
		||||
              <label for="minimalScopesMode">
 | 
			
		||||
                {{$t('settings.minimal_scopes_mode')}} {{$t('settings.instance_default', { value: minimalScopesModeDefault })}}
 | 
			
		||||
              </label>
 | 
			
		||||
            </li>
 | 
			
		||||
          </ul>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div class="setting-item">
 | 
			
		||||
          <h2>{{$t('settings.attachments')}}</h2>
 | 
			
		||||
          <ul class="setting-list">
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="hideAttachments" v-model="hideAttachmentsLocal">
 | 
			
		||||
              <label for="hideAttachments">{{$t('settings.hide_attachments_in_tl')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="hideAttachmentsInConv" v-model="hideAttachmentsInConvLocal">
 | 
			
		||||
              <label for="hideAttachmentsInConv">{{$t('settings.hide_attachments_in_convo')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <label for="maxThumbnails">{{$t('settings.max_thumbnails')}}</label>
 | 
			
		||||
              <input class="number-input" type="number" id="maxThumbnails" v-model.number="maxThumbnails" min="0" step="1">
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="hideNsfw" v-model="hideNsfwLocal">
 | 
			
		||||
              <label for="hideNsfw">{{$t('settings.nsfw_clickthrough')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <ul class="setting-list suboptions" >
 | 
			
		||||
              <li>
 | 
			
		||||
                <input :disabled="!hideNsfwLocal" type="checkbox" id="preloadImage" v-model="preloadImage">
 | 
			
		||||
                <label for="preloadImage">{{$t('settings.preload_images')}}</label>
 | 
			
		||||
              </li>
 | 
			
		||||
              <li>
 | 
			
		||||
                <input :disabled="!hideNsfwLocal" type="checkbox" id="useOneClickNsfw" v-model="useOneClickNsfw">
 | 
			
		||||
                <label for="useOneClickNsfw">{{$t('settings.use_one_click_nsfw')}}</label>
 | 
			
		||||
              </li>
 | 
			
		||||
            </ul>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="stopGifs" v-model="stopGifs">
 | 
			
		||||
              <label for="stopGifs">{{$t('settings.stop_gifs')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="loopVideo" v-model="loopVideoLocal">
 | 
			
		||||
              <label for="loopVideo">{{$t('settings.loop_video')}}</label>
 | 
			
		||||
              <ul class="setting-list suboptions" :class="[{disabled: !streamingLocal}]">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input :disabled="!loopVideoLocal || !loopSilentAvailable" type="checkbox" id="loopVideoSilentOnly" v-model="loopVideoSilentOnlyLocal">
 | 
			
		||||
                  <label for="loopVideoSilentOnly">{{$t('settings.loop_video_silent_only')}}</label>
 | 
			
		||||
                  <div v-if="!loopSilentAvailable" class="unavailable">
 | 
			
		||||
                    <i class="icon-globe"/>! {{$t('settings.limited_availability')}}
 | 
			
		||||
                  </div>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="playVideosInModal" v-model="playVideosInModal">
 | 
			
		||||
              <label for="playVideosInModal">{{$t('settings.play_videos_in_modal')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="useContainFit" v-model="useContainFit">
 | 
			
		||||
              <label for="useContainFit">{{$t('settings.use_contain_fit')}}</label>
 | 
			
		||||
            </li>
 | 
			
		||||
          </ul>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
       <div class="setting-item">
 | 
			
		||||
          <h2>{{$t('settings.notifications')}}</h2>
 | 
			
		||||
          <ul class="setting-list">
 | 
			
		||||
            <li>
 | 
			
		||||
              <input type="checkbox" id="webPushNotifications" v-model="webPushNotificationsLocal">
 | 
			
		||||
              <label for="webPushNotifications">
 | 
			
		||||
                {{$t('settings.enable_web_push_notifications')}}
 | 
			
		||||
              </label>
 | 
			
		||||
            </li>
 | 
			
		||||
          </ul>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
      <transition name="fade">
 | 
			
		||||
        <template v-if="currentSaveStateNotice">
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="currentSaveStateNotice.error"
 | 
			
		||||
            class="alert error"
 | 
			
		||||
            @click.prevent
 | 
			
		||||
          >
 | 
			
		||||
            {{ $t('settings.saving_err') }}
 | 
			
		||||
          </div>
 | 
			
		||||
      <div :label="$t('settings.theme')" >
 | 
			
		||||
        <div class="setting-item">
 | 
			
		||||
          <style-switcher></style-switcher>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="!currentSaveStateNotice.error"
 | 
			
		||||
            class="alert transparent"
 | 
			
		||||
            @click.prevent
 | 
			
		||||
          >
 | 
			
		||||
            {{ $t('settings.saving_ok') }}
 | 
			
		||||
          </div>
 | 
			
		||||
        </template>
 | 
			
		||||
      </transition>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="panel-body">
 | 
			
		||||
      <keep-alive>
 | 
			
		||||
        <tab-switcher>
 | 
			
		||||
          <div :label="$t('settings.general')">
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <h2>{{ $t('settings.interface') }}</h2>
 | 
			
		||||
              <ul class="setting-list">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <interface-language-switcher />
 | 
			
		||||
                </li>
 | 
			
		||||
                <li v-if="instanceSpecificPanelPresent">
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="hideISP"
 | 
			
		||||
                    v-model="hideISPLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="hideISP">{{ $t('settings.hide_isp') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <h2>{{ $t('nav.timeline') }}</h2>
 | 
			
		||||
              <ul class="setting-list">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="hideMutedPosts"
 | 
			
		||||
                    v-model="hideMutedPostsLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="hideMutedPosts">{{ $t('settings.hide_muted_posts') }} {{ $t('settings.instance_default', { value: hideMutedPostsDefault }) }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="collapseMessageWithSubject"
 | 
			
		||||
                    v-model="collapseMessageWithSubjectLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="collapseMessageWithSubject">
 | 
			
		||||
                    {{ $t('settings.collapse_subject') }} {{ $t('settings.instance_default', { value: collapseMessageWithSubjectDefault }) }}
 | 
			
		||||
                  </label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="streaming"
 | 
			
		||||
                    v-model="streamingLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="streaming">{{ $t('settings.streaming') }}</label>
 | 
			
		||||
                  <ul
 | 
			
		||||
                    class="setting-list suboptions"
 | 
			
		||||
                    :class="[{disabled: !streamingLocal}]"
 | 
			
		||||
                  >
 | 
			
		||||
                    <li>
 | 
			
		||||
                      <input
 | 
			
		||||
                        id="pauseOnUnfocused"
 | 
			
		||||
                        v-model="pauseOnUnfocusedLocal"
 | 
			
		||||
                        :disabled="!streamingLocal"
 | 
			
		||||
                        type="checkbox"
 | 
			
		||||
                      >
 | 
			
		||||
                      <label for="pauseOnUnfocused">{{ $t('settings.pause_on_unfocused') }}</label>
 | 
			
		||||
                    </li>
 | 
			
		||||
                  </ul>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="autoload"
 | 
			
		||||
                    v-model="autoLoadLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="autoload">{{ $t('settings.autoload') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="hoverPreview"
 | 
			
		||||
                    v-model="hoverPreviewLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="hoverPreview">{{ $t('settings.reply_link_preview') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <h2>{{ $t('settings.composing') }}</h2>
 | 
			
		||||
              <ul class="setting-list">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="scopeCopy"
 | 
			
		||||
                    v-model="scopeCopyLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="scopeCopy">
 | 
			
		||||
                    {{ $t('settings.scope_copy') }} {{ $t('settings.instance_default', { value: scopeCopyDefault }) }}
 | 
			
		||||
                  </label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="subjectHide"
 | 
			
		||||
                    v-model="alwaysShowSubjectInputLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="subjectHide">
 | 
			
		||||
                    {{ $t('settings.subject_input_always_show') }} {{ $t('settings.instance_default', { value: alwaysShowSubjectInputDefault }) }}
 | 
			
		||||
                  </label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <div>
 | 
			
		||||
                    {{ $t('settings.subject_line_behavior') }}
 | 
			
		||||
                    <label
 | 
			
		||||
                      for="subjectLineBehavior"
 | 
			
		||||
                      class="select"
 | 
			
		||||
                    >
 | 
			
		||||
                      <select
 | 
			
		||||
                        id="subjectLineBehavior"
 | 
			
		||||
                        v-model="subjectLineBehaviorLocal"
 | 
			
		||||
                      >
 | 
			
		||||
                        <option value="email">
 | 
			
		||||
                          {{ $t('settings.subject_line_email') }}
 | 
			
		||||
                          {{ subjectLineBehaviorDefault == 'email' ? $t('settings.instance_default_simple') : '' }}
 | 
			
		||||
                        </option>
 | 
			
		||||
                        <option value="masto">
 | 
			
		||||
                          {{ $t('settings.subject_line_mastodon') }}
 | 
			
		||||
                          {{ subjectLineBehaviorDefault == 'mastodon' ? $t('settings.instance_default_simple') : '' }}
 | 
			
		||||
                        </option>
 | 
			
		||||
                        <option value="noop">
 | 
			
		||||
                          {{ $t('settings.subject_line_noop') }}
 | 
			
		||||
                          {{ subjectLineBehaviorDefault == 'noop' ? $t('settings.instance_default_simple') : '' }}
 | 
			
		||||
                        </option>
 | 
			
		||||
                      </select>
 | 
			
		||||
                      <i class="icon-down-open" />
 | 
			
		||||
                    </label>
 | 
			
		||||
                  </div>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <div>
 | 
			
		||||
                    {{ $t('settings.post_status_content_type') }}
 | 
			
		||||
                    <label
 | 
			
		||||
                      for="postContentType"
 | 
			
		||||
                      class="select"
 | 
			
		||||
                    >
 | 
			
		||||
                      <select
 | 
			
		||||
                        id="postContentType"
 | 
			
		||||
                        v-model="postContentTypeLocal"
 | 
			
		||||
                      >
 | 
			
		||||
                        <option
 | 
			
		||||
                          v-for="postFormat in postFormats"
 | 
			
		||||
                          :key="postFormat"
 | 
			
		||||
                          :value="postFormat"
 | 
			
		||||
                        >
 | 
			
		||||
                          {{ $t(`post_status.content_type["${postFormat}"]`) }}
 | 
			
		||||
                          {{ postContentTypeDefault === postFormat ? $t('settings.instance_default_simple') : '' }}
 | 
			
		||||
                        </option>
 | 
			
		||||
                      </select>
 | 
			
		||||
                      <i class="icon-down-open" />
 | 
			
		||||
                    </label>
 | 
			
		||||
                  </div>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="minimalScopesMode"
 | 
			
		||||
                    v-model="minimalScopesModeLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="minimalScopesMode">
 | 
			
		||||
                    {{ $t('settings.minimal_scopes_mode') }} {{ $t('settings.instance_default', { value: minimalScopesModeDefault }) }}
 | 
			
		||||
                  </label>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <h2>{{ $t('settings.attachments') }}</h2>
 | 
			
		||||
              <ul class="setting-list">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="hideAttachments"
 | 
			
		||||
                    v-model="hideAttachmentsLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="hideAttachments">{{ $t('settings.hide_attachments_in_tl') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="hideAttachmentsInConv"
 | 
			
		||||
                    v-model="hideAttachmentsInConvLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="hideAttachmentsInConv">{{ $t('settings.hide_attachments_in_convo') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <label for="maxThumbnails">{{ $t('settings.max_thumbnails') }}</label>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="maxThumbnails"
 | 
			
		||||
                    v-model.number="maxThumbnails"
 | 
			
		||||
                    class="number-input"
 | 
			
		||||
                    type="number"
 | 
			
		||||
                    min="0"
 | 
			
		||||
                    step="1"
 | 
			
		||||
                  >
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="hideNsfw"
 | 
			
		||||
                    v-model="hideNsfwLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="hideNsfw">{{ $t('settings.nsfw_clickthrough') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <ul class="setting-list suboptions">
 | 
			
		||||
                  <li>
 | 
			
		||||
                    <input
 | 
			
		||||
                      id="preloadImage"
 | 
			
		||||
                      v-model="preloadImage"
 | 
			
		||||
                      :disabled="!hideNsfwLocal"
 | 
			
		||||
                      type="checkbox"
 | 
			
		||||
                    >
 | 
			
		||||
                    <label for="preloadImage">{{ $t('settings.preload_images') }}</label>
 | 
			
		||||
                  </li>
 | 
			
		||||
                  <li>
 | 
			
		||||
                    <input
 | 
			
		||||
                      id="useOneClickNsfw"
 | 
			
		||||
                      v-model="useOneClickNsfw"
 | 
			
		||||
                      :disabled="!hideNsfwLocal"
 | 
			
		||||
                      type="checkbox"
 | 
			
		||||
                    >
 | 
			
		||||
                    <label for="useOneClickNsfw">{{ $t('settings.use_one_click_nsfw') }}</label>
 | 
			
		||||
                  </li>
 | 
			
		||||
                </ul>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="stopGifs"
 | 
			
		||||
                    v-model="stopGifs"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="stopGifs">{{ $t('settings.stop_gifs') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="loopVideo"
 | 
			
		||||
                    v-model="loopVideoLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="loopVideo">{{ $t('settings.loop_video') }}</label>
 | 
			
		||||
                  <ul
 | 
			
		||||
                    class="setting-list suboptions"
 | 
			
		||||
                    :class="[{disabled: !streamingLocal}]"
 | 
			
		||||
                  >
 | 
			
		||||
                    <li>
 | 
			
		||||
                      <input
 | 
			
		||||
                        id="loopVideoSilentOnly"
 | 
			
		||||
                        v-model="loopVideoSilentOnlyLocal"
 | 
			
		||||
                        :disabled="!loopVideoLocal || !loopSilentAvailable"
 | 
			
		||||
                        type="checkbox"
 | 
			
		||||
                      >
 | 
			
		||||
                      <label for="loopVideoSilentOnly">{{ $t('settings.loop_video_silent_only') }}</label>
 | 
			
		||||
                      <div
 | 
			
		||||
                        v-if="!loopSilentAvailable"
 | 
			
		||||
                        class="unavailable"
 | 
			
		||||
                      >
 | 
			
		||||
                        <i class="icon-globe" />! {{ $t('settings.limited_availability') }}
 | 
			
		||||
                      </div>
 | 
			
		||||
                    </li>
 | 
			
		||||
                  </ul>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="playVideosInModal"
 | 
			
		||||
                    v-model="playVideosInModal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="playVideosInModal">{{ $t('settings.play_videos_in_modal') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="useContainFit"
 | 
			
		||||
                    v-model="useContainFit"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="useContainFit">{{ $t('settings.use_contain_fit') }}</label>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <h2>{{ $t('settings.notifications') }}</h2>
 | 
			
		||||
              <ul class="setting-list">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <input
 | 
			
		||||
                    id="webPushNotifications"
 | 
			
		||||
                    v-model="webPushNotificationsLocal"
 | 
			
		||||
                    type="checkbox"
 | 
			
		||||
                  >
 | 
			
		||||
                  <label for="webPushNotifications">
 | 
			
		||||
                    {{ $t('settings.enable_web_push_notifications') }}
 | 
			
		||||
                  </label>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div :label="$t('settings.theme')">
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <style-switcher />
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div :label="$t('settings.filtering')">
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <div class="select-multiple">
 | 
			
		||||
                <span class="label">{{ $t('settings.notification_visibility') }}</span>
 | 
			
		||||
                <ul class="option-list">
 | 
			
		||||
                  <li>
 | 
			
		||||
                    <input
 | 
			
		||||
                      id="notification-visibility-likes"
 | 
			
		||||
                      v-model="notificationVisibilityLocal.likes"
 | 
			
		||||
                      type="checkbox"
 | 
			
		||||
                    >
 | 
			
		||||
                    <label for="notification-visibility-likes">
 | 
			
		||||
                      {{ $t('settings.notification_visibility_likes') }}
 | 
			
		||||
                    </label>
 | 
			
		||||
                  </li>
 | 
			
		||||
                  <li>
 | 
			
		||||
                    <input
 | 
			
		||||
                      id="notification-visibility-repeats"
 | 
			
		||||
                      v-model="notificationVisibilityLocal.repeats"
 | 
			
		||||
                      type="checkbox"
 | 
			
		||||
                    >
 | 
			
		||||
                    <label for="notification-visibility-repeats">
 | 
			
		||||
                      {{ $t('settings.notification_visibility_repeats') }}
 | 
			
		||||
                    </label>
 | 
			
		||||
                  </li>
 | 
			
		||||
                  <li>
 | 
			
		||||
                    <input
 | 
			
		||||
                      id="notification-visibility-follows"
 | 
			
		||||
                      v-model="notificationVisibilityLocal.follows"
 | 
			
		||||
                      type="checkbox"
 | 
			
		||||
                    >
 | 
			
		||||
                    <label for="notification-visibility-follows">
 | 
			
		||||
                      {{ $t('settings.notification_visibility_follows') }}
 | 
			
		||||
                    </label>
 | 
			
		||||
                  </li>
 | 
			
		||||
                  <li>
 | 
			
		||||
                    <input
 | 
			
		||||
                      id="notification-visibility-mentions"
 | 
			
		||||
                      v-model="notificationVisibilityLocal.mentions"
 | 
			
		||||
                      type="checkbox"
 | 
			
		||||
                    >
 | 
			
		||||
                    <label for="notification-visibility-mentions">
 | 
			
		||||
                      {{ $t('settings.notification_visibility_mentions') }}
 | 
			
		||||
                    </label>
 | 
			
		||||
                  </li>
 | 
			
		||||
                </ul>
 | 
			
		||||
              </div>
 | 
			
		||||
              <div>
 | 
			
		||||
                {{ $t('settings.replies_in_timeline') }}
 | 
			
		||||
                <label
 | 
			
		||||
                  for="replyVisibility"
 | 
			
		||||
                  class="select"
 | 
			
		||||
                >
 | 
			
		||||
                  <select
 | 
			
		||||
                    id="replyVisibility"
 | 
			
		||||
                    v-model="replyVisibilityLocal"
 | 
			
		||||
                  >
 | 
			
		||||
                    <option
 | 
			
		||||
                      value="all"
 | 
			
		||||
                      selected
 | 
			
		||||
                    >{{ $t('settings.reply_visibility_all') }}</option>
 | 
			
		||||
                    <option value="following">{{ $t('settings.reply_visibility_following') }}</option>
 | 
			
		||||
                    <option value="self">{{ $t('settings.reply_visibility_self') }}</option>
 | 
			
		||||
                  </select>
 | 
			
		||||
                  <i class="icon-down-open" />
 | 
			
		||||
      <div :label="$t('settings.filtering')" >
 | 
			
		||||
        <div class="setting-item">
 | 
			
		||||
          <div class="select-multiple">
 | 
			
		||||
            <span class="label">{{$t('settings.notification_visibility')}}</span>
 | 
			
		||||
            <ul class="option-list">
 | 
			
		||||
              <li>
 | 
			
		||||
                <input type="checkbox" id="notification-visibility-likes" v-model="notificationVisibilityLocal.likes">
 | 
			
		||||
                <label for="notification-visibility-likes">
 | 
			
		||||
                  {{$t('settings.notification_visibility_likes')}}
 | 
			
		||||
                </label>
 | 
			
		||||
              </div>
 | 
			
		||||
              <div>
 | 
			
		||||
                <input
 | 
			
		||||
                  id="hidePostStats"
 | 
			
		||||
                  v-model="hidePostStatsLocal"
 | 
			
		||||
                  type="checkbox"
 | 
			
		||||
                >
 | 
			
		||||
                <label for="hidePostStats">
 | 
			
		||||
                  {{ $t('settings.hide_post_stats') }} {{ $t('settings.instance_default', { value: hidePostStatsDefault }) }}
 | 
			
		||||
              </li>
 | 
			
		||||
              <li>
 | 
			
		||||
                <input type="checkbox" id="notification-visibility-repeats" v-model="notificationVisibilityLocal.repeats">
 | 
			
		||||
                <label for="notification-visibility-repeats">
 | 
			
		||||
                {{$t('settings.notification_visibility_repeats')}}
 | 
			
		||||
                </label>
 | 
			
		||||
              </div>
 | 
			
		||||
              <div>
 | 
			
		||||
                <input
 | 
			
		||||
                  id="hideUserStats"
 | 
			
		||||
                  v-model="hideUserStatsLocal"
 | 
			
		||||
                  type="checkbox"
 | 
			
		||||
                >
 | 
			
		||||
                <label for="hideUserStats">
 | 
			
		||||
                  {{ $t('settings.hide_user_stats') }} {{ $t('settings.instance_default', { value: hideUserStatsDefault }) }}
 | 
			
		||||
              </li>
 | 
			
		||||
              <li>
 | 
			
		||||
                <input type="checkbox" id="notification-visibility-follows" v-model="notificationVisibilityLocal.follows">
 | 
			
		||||
                <label for="notification-visibility-follows">
 | 
			
		||||
                {{$t('settings.notification_visibility_follows')}}
 | 
			
		||||
                </label>
 | 
			
		||||
              </div>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <div>
 | 
			
		||||
                <p>{{ $t('settings.filtering_explanation') }}</p>
 | 
			
		||||
                <textarea
 | 
			
		||||
                  id="muteWords"
 | 
			
		||||
                  v-model="muteWordsString"
 | 
			
		||||
                />
 | 
			
		||||
              </div>
 | 
			
		||||
              <div>
 | 
			
		||||
                <input
 | 
			
		||||
                  id="hideFilteredStatuses"
 | 
			
		||||
                  v-model="hideFilteredStatusesLocal"
 | 
			
		||||
                  type="checkbox"
 | 
			
		||||
                >
 | 
			
		||||
                <label for="hideFilteredStatuses">
 | 
			
		||||
                  {{ $t('settings.hide_filtered_statuses') }} {{ $t('settings.instance_default', { value: hideFilteredStatusesDefault }) }}
 | 
			
		||||
              </li>
 | 
			
		||||
              <li>
 | 
			
		||||
                <input type="checkbox" id="notification-visibility-mentions" v-model="notificationVisibilityLocal.mentions">
 | 
			
		||||
                <label for="notification-visibility-mentions">
 | 
			
		||||
                {{$t('settings.notification_visibility_mentions')}}
 | 
			
		||||
                </label>
 | 
			
		||||
              </div>
 | 
			
		||||
            </div>
 | 
			
		||||
              </li>
 | 
			
		||||
            </ul>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div :label="$t('settings.version.title')">
 | 
			
		||||
            <div class="setting-item">
 | 
			
		||||
              <ul class="setting-list">
 | 
			
		||||
          <div>
 | 
			
		||||
            {{$t('settings.replies_in_timeline')}}
 | 
			
		||||
            <label for="replyVisibility" class="select">
 | 
			
		||||
              <select id="replyVisibility" v-model="replyVisibilityLocal">
 | 
			
		||||
                <option value="all" selected>{{$t('settings.reply_visibility_all')}}</option>
 | 
			
		||||
                <option value="following">{{$t('settings.reply_visibility_following')}}</option>
 | 
			
		||||
                <option value="self">{{$t('settings.reply_visibility_self')}}</option>
 | 
			
		||||
              </select>
 | 
			
		||||
              <i class="icon-down-open"/>
 | 
			
		||||
            </label>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div>
 | 
			
		||||
            <input type="checkbox" id="hidePostStats" v-model="hidePostStatsLocal">
 | 
			
		||||
            <label for="hidePostStats">
 | 
			
		||||
              {{$t('settings.hide_post_stats')}} {{$t('settings.instance_default', { value: hidePostStatsDefault })}}
 | 
			
		||||
            </label>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div>
 | 
			
		||||
            <input type="checkbox" id="hideUserStats" v-model="hideUserStatsLocal">
 | 
			
		||||
            <label for="hideUserStats">
 | 
			
		||||
              {{$t('settings.hide_user_stats')}} {{$t('settings.instance_default', { value: hideUserStatsDefault })}}
 | 
			
		||||
            </label>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="setting-item">
 | 
			
		||||
          <div>
 | 
			
		||||
            <p>{{$t('settings.filtering_explanation')}}</p>
 | 
			
		||||
            <textarea id="muteWords" v-model="muteWordsString"></textarea>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div>
 | 
			
		||||
            <input type="checkbox" id="hideFilteredStatuses" v-model="hideFilteredStatusesLocal">
 | 
			
		||||
            <label for="hideFilteredStatuses">
 | 
			
		||||
              {{$t('settings.hide_filtered_statuses')}} {{$t('settings.instance_default', { value: hideFilteredStatusesDefault })}}
 | 
			
		||||
            </label>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div :label="$t('settings.version.title')" >
 | 
			
		||||
        <div class="setting-item">
 | 
			
		||||
          <ul class="setting-list">
 | 
			
		||||
            <li>
 | 
			
		||||
              <p>{{$t('settings.version.backend_version')}}</p>
 | 
			
		||||
              <ul class="option-list">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <p>{{ $t('settings.version.backend_version') }}</p>
 | 
			
		||||
                  <ul class="option-list">
 | 
			
		||||
                    <li>
 | 
			
		||||
                      <a
 | 
			
		||||
                        :href="backendVersionLink"
 | 
			
		||||
                        target="_blank"
 | 
			
		||||
                      >{{ backendVersion }}</a>
 | 
			
		||||
                    </li>
 | 
			
		||||
                  </ul>
 | 
			
		||||
                </li>
 | 
			
		||||
                <li>
 | 
			
		||||
                  <p>{{ $t('settings.version.frontend_version') }}</p>
 | 
			
		||||
                  <ul class="option-list">
 | 
			
		||||
                    <li>
 | 
			
		||||
                      <a
 | 
			
		||||
                        :href="frontendVersionLink"
 | 
			
		||||
                        target="_blank"
 | 
			
		||||
                      >{{ frontendVersion }}</a>
 | 
			
		||||
                    </li>
 | 
			
		||||
                  </ul>
 | 
			
		||||
                  <a :href="backendVersionLink" target="_blank">{{backendVersion}}</a>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
        </tab-switcher>
 | 
			
		||||
      </keep-alive>
 | 
			
		||||
    </div>
 | 
			
		||||
            </li>
 | 
			
		||||
            <li>
 | 
			
		||||
              <p>{{$t('settings.version.frontend_version')}}</p>
 | 
			
		||||
              <ul class="option-list">
 | 
			
		||||
                <li>
 | 
			
		||||
                  <a :href="frontendVersionLink" target="_blank">{{frontendVersion}}</a>
 | 
			
		||||
                </li>
 | 
			
		||||
              </ul>
 | 
			
		||||
            </li>
 | 
			
		||||
          </ul>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </tab-switcher>
 | 
			
		||||
</keep-alive>
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./settings.js">
 | 
			
		||||
| 
						 | 
				
			
			@ -501,6 +327,7 @@
 | 
			
		|||
    min-width: 10em;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
  textarea {
 | 
			
		||||
    width: 100%;
 | 
			
		||||
    height: 100px;
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,207 +1,134 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="shadow-control"
 | 
			
		||||
    :class="{ disabled: !present }"
 | 
			
		||||
  >
 | 
			
		||||
    <div class="shadow-preview-container">
 | 
			
		||||
      <div
 | 
			
		||||
<div class="shadow-control" :class="{ disabled: !present }">
 | 
			
		||||
  <div class="shadow-preview-container">
 | 
			
		||||
    <div :disabled="!present" class="y-shift-control">
 | 
			
		||||
      <input
 | 
			
		||||
        v-model="selected.y"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        class="y-shift-control"
 | 
			
		||||
      >
 | 
			
		||||
        class="input-number"
 | 
			
		||||
        type="number">
 | 
			
		||||
      <div class="wrap">
 | 
			
		||||
        <input
 | 
			
		||||
          v-model="selected.y"
 | 
			
		||||
          :disabled="!present"
 | 
			
		||||
          class="input-number"
 | 
			
		||||
          type="number"
 | 
			
		||||
        >
 | 
			
		||||
        <div class="wrap">
 | 
			
		||||
          <input
 | 
			
		||||
            v-model="selected.y"
 | 
			
		||||
            :disabled="!present"
 | 
			
		||||
            class="input-range"
 | 
			
		||||
            type="range"
 | 
			
		||||
            max="20"
 | 
			
		||||
            min="-20"
 | 
			
		||||
          >
 | 
			
		||||
        </div>
 | 
			
		||||
          class="input-range"
 | 
			
		||||
          type="range"
 | 
			
		||||
          max="20"
 | 
			
		||||
          min="-20">
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="preview-window">
 | 
			
		||||
        <div
 | 
			
		||||
          class="preview-block"
 | 
			
		||||
          :style="style"
 | 
			
		||||
        />
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="preview-window">
 | 
			
		||||
      <div class="preview-block" :style="style"></div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div :disabled="!present" class="x-shift-control">
 | 
			
		||||
      <input
 | 
			
		||||
        v-model="selected.x"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        class="x-shift-control"
 | 
			
		||||
      >
 | 
			
		||||
        class="input-number"
 | 
			
		||||
        type="number">
 | 
			
		||||
      <div class="wrap">
 | 
			
		||||
        <input
 | 
			
		||||
          v-model="selected.x"
 | 
			
		||||
          :disabled="!present"
 | 
			
		||||
          class="input-number"
 | 
			
		||||
          type="number"
 | 
			
		||||
        >
 | 
			
		||||
        <div class="wrap">
 | 
			
		||||
          <input
 | 
			
		||||
            v-model="selected.x"
 | 
			
		||||
            :disabled="!present"
 | 
			
		||||
            class="input-range"
 | 
			
		||||
            type="range"
 | 
			
		||||
            max="20"
 | 
			
		||||
            min="-20"
 | 
			
		||||
          >
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <div class="shadow-tweak">
 | 
			
		||||
      <div
 | 
			
		||||
        :disabled="usingFallback"
 | 
			
		||||
        class="id-control style-control"
 | 
			
		||||
      >
 | 
			
		||||
        <label
 | 
			
		||||
          for="shadow-switcher"
 | 
			
		||||
          class="select"
 | 
			
		||||
          :disabled="!ready || usingFallback"
 | 
			
		||||
        >
 | 
			
		||||
          <select
 | 
			
		||||
            id="shadow-switcher"
 | 
			
		||||
            v-model="selectedId"
 | 
			
		||||
            class="shadow-switcher"
 | 
			
		||||
            :disabled="!ready || usingFallback"
 | 
			
		||||
          >
 | 
			
		||||
            <option
 | 
			
		||||
              v-for="(shadow, index) in cValue"
 | 
			
		||||
              :key="index"
 | 
			
		||||
              :value="index"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.style.shadows.shadow_id', { value: index }) }}
 | 
			
		||||
            </option>
 | 
			
		||||
          </select>
 | 
			
		||||
          <i class="icon-down-open" />
 | 
			
		||||
        </label>
 | 
			
		||||
        <button
 | 
			
		||||
          class="btn btn-default"
 | 
			
		||||
          :disabled="!ready || !present"
 | 
			
		||||
          @click="del"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="icon-cancel" />
 | 
			
		||||
        </button>
 | 
			
		||||
        <button
 | 
			
		||||
          class="btn btn-default"
 | 
			
		||||
          :disabled="!moveUpValid"
 | 
			
		||||
          @click="moveUp"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="icon-up-open" />
 | 
			
		||||
        </button>
 | 
			
		||||
        <button
 | 
			
		||||
          class="btn btn-default"
 | 
			
		||||
          :disabled="!moveDnValid"
 | 
			
		||||
          @click="moveDn"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="icon-down-open" />
 | 
			
		||||
        </button>
 | 
			
		||||
        <button
 | 
			
		||||
          class="btn btn-default"
 | 
			
		||||
          :disabled="usingFallback"
 | 
			
		||||
          @click="add"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="icon-plus" />
 | 
			
		||||
        </button>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        class="inset-control style-control"
 | 
			
		||||
      >
 | 
			
		||||
        <label
 | 
			
		||||
          for="inset"
 | 
			
		||||
          class="label"
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('settings.style.shadows.inset') }}
 | 
			
		||||
        </label>
 | 
			
		||||
        <input
 | 
			
		||||
          id="inset"
 | 
			
		||||
          v-model="selected.inset"
 | 
			
		||||
          :disabled="!present"
 | 
			
		||||
          name="inset"
 | 
			
		||||
          class="input-inset"
 | 
			
		||||
          type="checkbox"
 | 
			
		||||
        >
 | 
			
		||||
        <label
 | 
			
		||||
          class="checkbox-label"
 | 
			
		||||
          for="inset"
 | 
			
		||||
        />
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        class="blur-control style-control"
 | 
			
		||||
      >
 | 
			
		||||
        <label
 | 
			
		||||
          for="spread"
 | 
			
		||||
          class="label"
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('settings.style.shadows.blur') }}
 | 
			
		||||
        </label>
 | 
			
		||||
        <input
 | 
			
		||||
          id="blur"
 | 
			
		||||
          v-model="selected.blur"
 | 
			
		||||
          :disabled="!present"
 | 
			
		||||
          name="blur"
 | 
			
		||||
          class="input-range"
 | 
			
		||||
          type="range"
 | 
			
		||||
          max="20"
 | 
			
		||||
          min="0"
 | 
			
		||||
        >
 | 
			
		||||
        <input
 | 
			
		||||
          v-model="selected.blur"
 | 
			
		||||
          :disabled="!present"
 | 
			
		||||
          class="input-number"
 | 
			
		||||
          type="number"
 | 
			
		||||
          min="0"
 | 
			
		||||
        >
 | 
			
		||||
          min="-20">
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        class="spread-control style-control"
 | 
			
		||||
      >
 | 
			
		||||
        <label
 | 
			
		||||
          for="spread"
 | 
			
		||||
          class="label"
 | 
			
		||||
        >
 | 
			
		||||
          {{ $t('settings.style.shadows.spread') }}
 | 
			
		||||
        </label>
 | 
			
		||||
        <input
 | 
			
		||||
          id="spread"
 | 
			
		||||
          v-model="selected.spread"
 | 
			
		||||
          :disabled="!present"
 | 
			
		||||
          name="spread"
 | 
			
		||||
          class="input-range"
 | 
			
		||||
          type="range"
 | 
			
		||||
          max="20"
 | 
			
		||||
          min="-20"
 | 
			
		||||
        >
 | 
			
		||||
        <input
 | 
			
		||||
          v-model="selected.spread"
 | 
			
		||||
          :disabled="!present"
 | 
			
		||||
          class="input-number"
 | 
			
		||||
          type="number"
 | 
			
		||||
        >
 | 
			
		||||
      </div>
 | 
			
		||||
      <ColorInput
 | 
			
		||||
        v-model="selected.color"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        :label="$t('settings.style.common.color')"
 | 
			
		||||
        name="shadow"
 | 
			
		||||
      />
 | 
			
		||||
      <OpacityInput
 | 
			
		||||
        v-model="selected.alpha"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
      />
 | 
			
		||||
      <p>
 | 
			
		||||
        {{ $t('settings.style.shadows.hint') }}
 | 
			
		||||
      </p>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
 | 
			
		||||
  <div class="shadow-tweak">
 | 
			
		||||
    <div :disabled="usingFallback" class="id-control style-control">
 | 
			
		||||
      <label for="shadow-switcher" class="select" :disabled="!ready || usingFallback">
 | 
			
		||||
        <select
 | 
			
		||||
          v-model="selectedId" class="shadow-switcher"
 | 
			
		||||
          :disabled="!ready || usingFallback"
 | 
			
		||||
          id="shadow-switcher">
 | 
			
		||||
          <option v-for="(shadow, index) in cValue" :value="index">
 | 
			
		||||
            {{$t('settings.style.shadows.shadow_id', { value: index })}}
 | 
			
		||||
          </option>
 | 
			
		||||
        </select>
 | 
			
		||||
        <i class="icon-down-open"/>
 | 
			
		||||
      </label>
 | 
			
		||||
      <button class="btn btn-default" :disabled="!ready || !present" @click="del">
 | 
			
		||||
        <i class="icon-cancel"/>
 | 
			
		||||
      </button>
 | 
			
		||||
      <button class="btn btn-default" :disabled="!moveUpValid" @click="moveUp">
 | 
			
		||||
        <i class="icon-up-open"/>
 | 
			
		||||
      </button>
 | 
			
		||||
      <button class="btn btn-default" :disabled="!moveDnValid" @click="moveDn">
 | 
			
		||||
        <i class="icon-down-open"/>
 | 
			
		||||
      </button>
 | 
			
		||||
      <button class="btn btn-default" :disabled="usingFallback" @click="add">
 | 
			
		||||
        <i class="icon-plus"/>
 | 
			
		||||
      </button>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div :disabled="!present" class="inset-control style-control">
 | 
			
		||||
      <label for="inset" class="label">
 | 
			
		||||
        {{$t('settings.style.shadows.inset')}}
 | 
			
		||||
      </label>
 | 
			
		||||
      <input
 | 
			
		||||
        v-model="selected.inset"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        name="inset"
 | 
			
		||||
        id="inset"
 | 
			
		||||
        class="input-inset"
 | 
			
		||||
        type="checkbox">
 | 
			
		||||
      <label class="checkbox-label" for="inset"></label>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div :disabled="!present" class="blur-control style-control">
 | 
			
		||||
      <label for="spread" class="label">
 | 
			
		||||
        {{$t('settings.style.shadows.blur')}}
 | 
			
		||||
      </label>
 | 
			
		||||
      <input
 | 
			
		||||
        v-model="selected.blur"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        name="blur"
 | 
			
		||||
        id="blur"
 | 
			
		||||
        class="input-range"
 | 
			
		||||
        type="range"
 | 
			
		||||
        max="20"
 | 
			
		||||
        min="0">
 | 
			
		||||
      <input
 | 
			
		||||
        v-model="selected.blur"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        class="input-number"
 | 
			
		||||
        type="number"
 | 
			
		||||
        min="0">
 | 
			
		||||
    </div>
 | 
			
		||||
    <div :disabled="!present" class="spread-control style-control">
 | 
			
		||||
      <label for="spread" class="label">
 | 
			
		||||
        {{$t('settings.style.shadows.spread')}}
 | 
			
		||||
      </label>
 | 
			
		||||
      <input
 | 
			
		||||
        v-model="selected.spread"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        name="spread"
 | 
			
		||||
        id="spread"
 | 
			
		||||
        class="input-range"
 | 
			
		||||
        type="range"
 | 
			
		||||
        max="20"
 | 
			
		||||
        min="-20">
 | 
			
		||||
      <input
 | 
			
		||||
        v-model="selected.spread"
 | 
			
		||||
        :disabled="!present"
 | 
			
		||||
        class="input-number"
 | 
			
		||||
        type="number">
 | 
			
		||||
    </div>
 | 
			
		||||
    <ColorInput
 | 
			
		||||
      v-model="selected.color"
 | 
			
		||||
      :disabled="!present"
 | 
			
		||||
      :label="$t('settings.style.common.color')"
 | 
			
		||||
      name="shadow"/>
 | 
			
		||||
    <OpacityInput
 | 
			
		||||
      v-model="selected.alpha"
 | 
			
		||||
      :disabled="!present"/>
 | 
			
		||||
    <p>
 | 
			
		||||
      {{$t('settings.style.shadows.hint')}}
 | 
			
		||||
    </p>
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./shadow_control.js" ></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,90 +1,58 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="side-drawer-container"
 | 
			
		||||
  <div class="side-drawer-container"
 | 
			
		||||
    :class="{ 'side-drawer-container-closed': closed, 'side-drawer-container-open': !closed }"
 | 
			
		||||
  >
 | 
			
		||||
    <div
 | 
			
		||||
      class="side-drawer-darken"
 | 
			
		||||
      :class="{ 'side-drawer-darken-closed': closed}"
 | 
			
		||||
    />
 | 
			
		||||
    <div
 | 
			
		||||
      class="side-drawer"
 | 
			
		||||
    <div class="side-drawer-darken" :class="{ 'side-drawer-darken-closed': closed}" />
 | 
			
		||||
    <div class="side-drawer"
 | 
			
		||||
      :class="{'side-drawer-closed': closed}"
 | 
			
		||||
      @touchstart="touchStart"
 | 
			
		||||
      @touchmove="touchMove"
 | 
			
		||||
    >
 | 
			
		||||
      <div
 | 
			
		||||
        class="side-drawer-heading"
 | 
			
		||||
        @click="toggleDrawer"
 | 
			
		||||
      >
 | 
			
		||||
        <UserCard
 | 
			
		||||
          v-if="currentUser"
 | 
			
		||||
          :user="currentUser"
 | 
			
		||||
          :hide-bio="true"
 | 
			
		||||
        />
 | 
			
		||||
        <div
 | 
			
		||||
          v-else
 | 
			
		||||
          class="side-drawer-logo-wrapper"
 | 
			
		||||
        >
 | 
			
		||||
          <img :src="logo">
 | 
			
		||||
          <span>{{ sitename }}</span>
 | 
			
		||||
      <div class="side-drawer-heading" @click="toggleDrawer">
 | 
			
		||||
        <UserCard :user="currentUser" :hideBio="true" v-if="currentUser"/>
 | 
			
		||||
        <div class="side-drawer-logo-wrapper" v-else>
 | 
			
		||||
          <img :src="logo"/>
 | 
			
		||||
          <span>{{sitename}}</span>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <ul>
 | 
			
		||||
        <li
 | 
			
		||||
          v-if="!currentUser"
 | 
			
		||||
          @click="toggleDrawer"
 | 
			
		||||
        >
 | 
			
		||||
        <li v-if="!currentUser" @click="toggleDrawer">
 | 
			
		||||
          <router-link :to="{ name: 'login' }">
 | 
			
		||||
            {{ $t("login.login") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li
 | 
			
		||||
          v-if="currentUser"
 | 
			
		||||
          @click="toggleDrawer"
 | 
			
		||||
        >
 | 
			
		||||
        <li v-if="currentUser" @click="toggleDrawer">
 | 
			
		||||
          <router-link :to="{ name: 'dms', params: { username: currentUser.screen_name } }">
 | 
			
		||||
            {{ $t("nav.dms") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
      </ul>
 | 
			
		||||
      <ul>
 | 
			
		||||
        <li
 | 
			
		||||
          v-if="currentUser"
 | 
			
		||||
          @click="toggleDrawer"
 | 
			
		||||
        >
 | 
			
		||||
        <li v-if="currentUser" @click="toggleDrawer">
 | 
			
		||||
          <router-link :to="{ name: 'friends' }">
 | 
			
		||||
            {{ $t("nav.timeline") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li
 | 
			
		||||
          v-if="currentUser && currentUser.locked"
 | 
			
		||||
          @click="toggleDrawer"
 | 
			
		||||
        >
 | 
			
		||||
          <router-link to="/friend-requests">
 | 
			
		||||
        <li v-if="currentUser && currentUser.locked" @click="toggleDrawer">
 | 
			
		||||
          <router-link to='/friend-requests'>
 | 
			
		||||
            {{ $t("nav.friend_requests") }}
 | 
			
		||||
            <span
 | 
			
		||||
              v-if="followRequestCount > 0"
 | 
			
		||||
              class="badge follow-request-count"
 | 
			
		||||
            >
 | 
			
		||||
              {{ followRequestCount }}
 | 
			
		||||
            <span v-if='followRequestCount > 0' class="badge follow-request-count">
 | 
			
		||||
              {{followRequestCount}}
 | 
			
		||||
            </span>
 | 
			
		||||
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li @click="toggleDrawer">
 | 
			
		||||
          <router-link to="/main/public">
 | 
			
		||||
          <router-link to='/main/public'>
 | 
			
		||||
            {{ $t("nav.public_tl") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li @click="toggleDrawer">
 | 
			
		||||
          <router-link to="/main/all">
 | 
			
		||||
          <router-link to='/main/all'>
 | 
			
		||||
            {{ $t("nav.twkn") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li
 | 
			
		||||
          v-if="currentUser && chat"
 | 
			
		||||
          @click="toggleDrawer"
 | 
			
		||||
        >
 | 
			
		||||
        <li v-if="currentUser && chat" @click="toggleDrawer">
 | 
			
		||||
          <router-link :to="{ name: 'chat' }">
 | 
			
		||||
            {{ $t("nav.chat") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
| 
						 | 
				
			
			@ -96,10 +64,7 @@
 | 
			
		|||
            {{ $t("nav.user_search") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li
 | 
			
		||||
          v-if="currentUser && suggestionsEnabled"
 | 
			
		||||
          @click="toggleDrawer"
 | 
			
		||||
        >
 | 
			
		||||
        <li v-if="currentUser && suggestionsEnabled" @click="toggleDrawer">
 | 
			
		||||
          <router-link :to="{ name: 'who-to-follow' }">
 | 
			
		||||
            {{ $t("nav.who_to_follow") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
| 
						 | 
				
			
			@ -114,24 +79,17 @@
 | 
			
		|||
            {{ $t("nav.about") }}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </li>
 | 
			
		||||
        <li
 | 
			
		||||
          v-if="currentUser"
 | 
			
		||||
          @click="toggleDrawer"
 | 
			
		||||
        >
 | 
			
		||||
          <a
 | 
			
		||||
            href="#"
 | 
			
		||||
            @click="doLogout"
 | 
			
		||||
          >
 | 
			
		||||
        <li v-if="currentUser" @click="toggleDrawer">
 | 
			
		||||
          <a @click="doLogout" href="#">
 | 
			
		||||
            {{ $t("login.logout") }}
 | 
			
		||||
          </a>
 | 
			
		||||
        </li>
 | 
			
		||||
      </ul>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div
 | 
			
		||||
      class="side-drawer-click-outside"
 | 
			
		||||
      :class="{'side-drawer-click-outside-closed': closed}"
 | 
			
		||||
    <div class="side-drawer-click-outside"
 | 
			
		||||
      @click.stop.prevent="toggleDrawer"
 | 
			
		||||
    />
 | 
			
		||||
      :class="{'side-drawer-click-outside-closed': closed}"
 | 
			
		||||
    ></div>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -210,10 +210,10 @@ const Status = {
 | 
			
		|||
      if (!this.status.summary) return ''
 | 
			
		||||
      const decodedSummary = unescape(this.status.summary)
 | 
			
		||||
      const behavior = typeof this.$store.state.config.subjectLineBehavior === 'undefined'
 | 
			
		||||
        ? this.$store.state.instance.subjectLineBehavior
 | 
			
		||||
        : this.$store.state.config.subjectLineBehavior
 | 
			
		||||
            ? this.$store.state.instance.subjectLineBehavior
 | 
			
		||||
            : this.$store.state.config.subjectLineBehavior
 | 
			
		||||
      const startsWithRe = decodedSummary.match(/^re[: ]/i)
 | 
			
		||||
      if ((behavior !== 'noop' && startsWithRe) || behavior === 'masto') {
 | 
			
		||||
      if (behavior !== 'noop' && startsWithRe || behavior === 'masto') {
 | 
			
		||||
        return decodedSummary
 | 
			
		||||
      } else if (behavior === 'email') {
 | 
			
		||||
        return 're: '.concat(decodedSummary)
 | 
			
		||||
| 
						 | 
				
			
			@ -350,7 +350,7 @@ const Status = {
 | 
			
		|||
        this.preview = find(statuses, { 'id': targetId })
 | 
			
		||||
        // or if we have to fetch it
 | 
			
		||||
        if (!this.preview) {
 | 
			
		||||
          this.$store.state.api.backendInteractor.fetchStatus({ id }).then((status) => {
 | 
			
		||||
          this.$store.state.api.backendInteractor.fetchStatus({id}).then((status) => {
 | 
			
		||||
            this.preview = status
 | 
			
		||||
          })
 | 
			
		||||
        }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,366 +1,152 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    v-if="!hideStatus"
 | 
			
		||||
    class="status-el"
 | 
			
		||||
    :class="[{ 'status-el_focused': isFocused }, { 'status-conversation': inlineExpanded }]"
 | 
			
		||||
  >
 | 
			
		||||
  <div class="status-el" v-if="!hideStatus" :class="[{ 'status-el_focused': isFocused }, { 'status-conversation': inlineExpanded }]">
 | 
			
		||||
    <template v-if="muted && !isPreview">
 | 
			
		||||
      <div class="media status container muted">
 | 
			
		||||
        <small>
 | 
			
		||||
          <router-link :to="userProfileLink">
 | 
			
		||||
            {{ status.user.screen_name }}
 | 
			
		||||
            {{status.user.screen_name}}
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </small>
 | 
			
		||||
        <small class="muteWords">{{ muteWordHits.join(', ') }}</small>
 | 
			
		||||
        <a
 | 
			
		||||
          href="#"
 | 
			
		||||
          class="unmute"
 | 
			
		||||
          @click.prevent="toggleMute"
 | 
			
		||||
        ><i class="button-icon icon-eye-off" /></a>
 | 
			
		||||
        <small class="muteWords">{{muteWordHits.join(', ')}}</small>
 | 
			
		||||
        <a href="#" class="unmute" @click.prevent="toggleMute"><i class="button-icon icon-eye-off"></i></a>
 | 
			
		||||
      </div>
 | 
			
		||||
    </template>
 | 
			
		||||
    <template v-else>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="retweet && !noHeading && !inConversation"
 | 
			
		||||
        :class="[repeaterClass, { highlighted: repeaterStyle }]"
 | 
			
		||||
        :style="[repeaterStyle]"
 | 
			
		||||
        class="media container retweet-info"
 | 
			
		||||
      >
 | 
			
		||||
        <UserAvatar
 | 
			
		||||
          v-if="retweet"
 | 
			
		||||
          class="media-left"
 | 
			
		||||
          :better-shadow="betterShadow"
 | 
			
		||||
          :src="statusoid.user.profile_image_url_original"
 | 
			
		||||
        />
 | 
			
		||||
      <div v-if="retweet && !noHeading && !inConversation" :class="[repeaterClass, { highlighted: repeaterStyle }]" :style="[repeaterStyle]" class="media container retweet-info">
 | 
			
		||||
        <UserAvatar class="media-left" v-if="retweet" :betterShadow="betterShadow" :src="statusoid.user.profile_image_url_original"/>
 | 
			
		||||
        <div class="media-body faint">
 | 
			
		||||
          <span class="user-name">
 | 
			
		||||
            <router-link
 | 
			
		||||
              v-if="retweeterHtml"
 | 
			
		||||
              :to="retweeterProfileLink"
 | 
			
		||||
              v-html="retweeterHtml"
 | 
			
		||||
            />
 | 
			
		||||
            <router-link
 | 
			
		||||
              v-else
 | 
			
		||||
              :to="retweeterProfileLink"
 | 
			
		||||
            >{{ retweeter }}</router-link>
 | 
			
		||||
            <router-link v-if="retweeterHtml" :to="retweeterProfileLink" v-html="retweeterHtml"/>
 | 
			
		||||
            <router-link v-else :to="retweeterProfileLink">{{retweeter}}</router-link>
 | 
			
		||||
          </span>
 | 
			
		||||
          <i
 | 
			
		||||
            class="fa icon-retweet retweeted"
 | 
			
		||||
            :title="$t('tool_tip.repeat')"
 | 
			
		||||
          />
 | 
			
		||||
          {{ $t('timeline.repeated') }}
 | 
			
		||||
          <i class='fa icon-retweet retweeted' :title="$t('tool_tip.repeat')"></i>
 | 
			
		||||
          {{$t('timeline.repeated')}}
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
      <div
 | 
			
		||||
        :class="[userClass, { highlighted: userStyle, 'is-retweet': retweet && !inConversation }]"
 | 
			
		||||
        :style="[ userStyle ]"
 | 
			
		||||
        class="media status"
 | 
			
		||||
      >
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="!noHeading"
 | 
			
		||||
          class="media-left"
 | 
			
		||||
        >
 | 
			
		||||
          <router-link
 | 
			
		||||
            :to="userProfileLink"
 | 
			
		||||
            @click.stop.prevent.capture.native="toggleUserExpanded"
 | 
			
		||||
          >
 | 
			
		||||
            <UserAvatar
 | 
			
		||||
              :compact="compact"
 | 
			
		||||
              :better-shadow="betterShadow"
 | 
			
		||||
              :src="status.user.profile_image_url_original"
 | 
			
		||||
            />
 | 
			
		||||
      <div :class="[userClass, { highlighted: userStyle, 'is-retweet': retweet && !inConversation }]" :style="[ userStyle ]" class="media status">
 | 
			
		||||
        <div v-if="!noHeading" class="media-left">
 | 
			
		||||
          <router-link :to="userProfileLink" @click.stop.prevent.capture.native="toggleUserExpanded">
 | 
			
		||||
            <UserAvatar :compact="compact" :betterShadow="betterShadow" :src="status.user.profile_image_url_original"/>
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="status-body">
 | 
			
		||||
          <UserCard
 | 
			
		||||
            v-if="userExpanded"
 | 
			
		||||
            :user="status.user"
 | 
			
		||||
            :rounded="true"
 | 
			
		||||
            :bordered="true"
 | 
			
		||||
            class="status-usercard"
 | 
			
		||||
          />
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="!noHeading"
 | 
			
		||||
            class="media-heading"
 | 
			
		||||
          >
 | 
			
		||||
          <UserCard :user="status.user" :rounded="true" :bordered="true" class="status-usercard" v-if="userExpanded"/>
 | 
			
		||||
          <div v-if="!noHeading" class="media-heading">
 | 
			
		||||
            <div class="heading-name-row">
 | 
			
		||||
              <div class="name-and-account-name">
 | 
			
		||||
                <h4
 | 
			
		||||
                  v-if="status.user.name_html"
 | 
			
		||||
                  class="user-name"
 | 
			
		||||
                  v-html="status.user.name_html"
 | 
			
		||||
                />
 | 
			
		||||
                <h4
 | 
			
		||||
                  v-else
 | 
			
		||||
                  class="user-name"
 | 
			
		||||
                >
 | 
			
		||||
                  {{ status.user.name }}
 | 
			
		||||
                </h4>
 | 
			
		||||
                <router-link
 | 
			
		||||
                  class="account-name"
 | 
			
		||||
                  :to="userProfileLink"
 | 
			
		||||
                >
 | 
			
		||||
                  {{ status.user.screen_name }}
 | 
			
		||||
                <h4 class="user-name" v-if="status.user.name_html" v-html="status.user.name_html"></h4>
 | 
			
		||||
                <h4 class="user-name" v-else>{{status.user.name}}</h4>
 | 
			
		||||
                <router-link class="account-name" :to="userProfileLink">
 | 
			
		||||
                  {{status.user.screen_name}}
 | 
			
		||||
                </router-link>
 | 
			
		||||
              </div>
 | 
			
		||||
 | 
			
		||||
              <span class="heading-right">
 | 
			
		||||
                <router-link
 | 
			
		||||
                  class="timeago faint-link"
 | 
			
		||||
                  :to="{ name: 'conversation', params: { id: status.id } }"
 | 
			
		||||
                >
 | 
			
		||||
                  <timeago
 | 
			
		||||
                    :since="status.created_at"
 | 
			
		||||
                    :auto-update="60"
 | 
			
		||||
                  />
 | 
			
		||||
                <router-link class="timeago faint-link" :to="{ name: 'conversation', params: { id: status.id } }">
 | 
			
		||||
                  <timeago :since="status.created_at" :auto-update="60"></timeago>
 | 
			
		||||
                </router-link>
 | 
			
		||||
                <div
 | 
			
		||||
                  v-if="status.visibility"
 | 
			
		||||
                  class="button-icon visibility-icon"
 | 
			
		||||
                >
 | 
			
		||||
                  <i
 | 
			
		||||
                    :class="visibilityIcon(status.visibility)"
 | 
			
		||||
                    :title="status.visibility | capitalize"
 | 
			
		||||
                  />
 | 
			
		||||
                <div class="button-icon visibility-icon" v-if="status.visibility">
 | 
			
		||||
                  <i :class="visibilityIcon(status.visibility)" :title="status.visibility | capitalize"></i>
 | 
			
		||||
                </div>
 | 
			
		||||
                <a
 | 
			
		||||
                  v-if="!status.is_local && !isPreview"
 | 
			
		||||
                  :href="status.external_url"
 | 
			
		||||
                  target="_blank"
 | 
			
		||||
                  class="source_url"
 | 
			
		||||
                  title="Source"
 | 
			
		||||
                >
 | 
			
		||||
                  <i class="button-icon icon-link-ext-alt" />
 | 
			
		||||
                <a :href="status.external_url" target="_blank" v-if="!status.is_local && !isPreview" class="source_url" title="Source">
 | 
			
		||||
                  <i class="button-icon icon-link-ext-alt"></i>
 | 
			
		||||
                </a>
 | 
			
		||||
                <template v-if="expandable && !isPreview">
 | 
			
		||||
                  <a
 | 
			
		||||
                    href="#"
 | 
			
		||||
                    title="Expand"
 | 
			
		||||
                    @click.prevent="toggleExpanded"
 | 
			
		||||
                  >
 | 
			
		||||
                    <i class="button-icon icon-plus-squared" />
 | 
			
		||||
                  <a href="#" @click.prevent="toggleExpanded" title="Expand">
 | 
			
		||||
                    <i class="button-icon icon-plus-squared"></i>
 | 
			
		||||
                  </a>
 | 
			
		||||
                </template>
 | 
			
		||||
                <a
 | 
			
		||||
                  v-if="unmuted"
 | 
			
		||||
                  href="#"
 | 
			
		||||
                  @click.prevent="toggleMute"
 | 
			
		||||
                ><i class="button-icon icon-eye-off" /></a>
 | 
			
		||||
                <a href="#" @click.prevent="toggleMute" v-if="unmuted"><i class="button-icon icon-eye-off"></i></a>
 | 
			
		||||
              </span>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <div class="heading-reply-row">
 | 
			
		||||
              <div
 | 
			
		||||
                v-if="isReply"
 | 
			
		||||
                class="reply-to-and-accountname"
 | 
			
		||||
              >
 | 
			
		||||
                <a
 | 
			
		||||
                  class="reply-to"
 | 
			
		||||
                  href="#"
 | 
			
		||||
              <div v-if="isReply" class="reply-to-and-accountname">
 | 
			
		||||
                <a class="reply-to"
 | 
			
		||||
                  href="#" @click.prevent="gotoOriginal(status.in_reply_to_status_id)"
 | 
			
		||||
                  :aria-label="$t('tool_tip.reply')"
 | 
			
		||||
                  @click.prevent="gotoOriginal(status.in_reply_to_status_id)"
 | 
			
		||||
                  @mouseenter.prevent.stop="replyEnter(status.in_reply_to_status_id, $event)"
 | 
			
		||||
                  @mouseleave.prevent.stop="replyLeave()"
 | 
			
		||||
                >
 | 
			
		||||
                  <i
 | 
			
		||||
                    v-if="!isPreview"
 | 
			
		||||
                    class="button-icon icon-reply"
 | 
			
		||||
                  />
 | 
			
		||||
                  <span class="faint-link reply-to-text">{{ $t('status.reply_to') }}</span>
 | 
			
		||||
                  <i class="button-icon icon-reply" v-if="!isPreview"></i>
 | 
			
		||||
                  <span class="faint-link reply-to-text">{{$t('status.reply_to')}}</span>
 | 
			
		||||
                </a>
 | 
			
		||||
                <router-link :to="replyProfileLink">
 | 
			
		||||
                  {{ replyToName }}
 | 
			
		||||
                  {{replyToName}}
 | 
			
		||||
                </router-link>
 | 
			
		||||
                <span
 | 
			
		||||
                  v-if="replies && replies.length"
 | 
			
		||||
                  class="faint replies-separator"
 | 
			
		||||
                >
 | 
			
		||||
                <span class="faint replies-separator" v-if="replies && replies.length">
 | 
			
		||||
                  -
 | 
			
		||||
                </span>
 | 
			
		||||
              </div>
 | 
			
		||||
              <div
 | 
			
		||||
                v-if="inConversation && !isPreview"
 | 
			
		||||
                class="replies"
 | 
			
		||||
              >
 | 
			
		||||
                <span
 | 
			
		||||
                  v-if="replies && replies.length"
 | 
			
		||||
                  class="faint"
 | 
			
		||||
                >{{ $t('status.replies_list') }}</span>
 | 
			
		||||
                <template
 | 
			
		||||
                  v-if="replies"
 | 
			
		||||
                >
 | 
			
		||||
                  <span
 | 
			
		||||
                    v-for="reply in replies"
 | 
			
		||||
                    :key="reply.name"
 | 
			
		||||
                    class="reply-link faint"
 | 
			
		||||
                  >
 | 
			
		||||
                    <a
 | 
			
		||||
                      href="#"
 | 
			
		||||
                      @click.prevent="gotoOriginal(reply.id)"
 | 
			
		||||
                      @mouseenter="replyEnter(reply.id, $event)"
 | 
			
		||||
                      @mouseout="replyLeave()"
 | 
			
		||||
                    >{{ reply.name }}</a>
 | 
			
		||||
                  </span>
 | 
			
		||||
                </template>
 | 
			
		||||
              <div class="replies" v-if="inConversation && !isPreview">
 | 
			
		||||
                <span class="faint" v-if="replies && replies.length">{{$t('status.replies_list')}}</span>
 | 
			
		||||
                <span class="reply-link faint" v-if="replies" v-for="reply in replies">
 | 
			
		||||
                  <a href="#" @click.prevent="gotoOriginal(reply.id)" @mouseenter="replyEnter(reply.id, $event)" @mouseout="replyLeave()">{{reply.name}}</a>
 | 
			
		||||
                </span>
 | 
			
		||||
              </div>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="showPreview"
 | 
			
		||||
            class="status-preview-container"
 | 
			
		||||
          >
 | 
			
		||||
            <status
 | 
			
		||||
              v-if="preview"
 | 
			
		||||
              class="status-preview"
 | 
			
		||||
              :is-preview="true"
 | 
			
		||||
              :statusoid="preview"
 | 
			
		||||
              :compact="true"
 | 
			
		||||
            />
 | 
			
		||||
            <div
 | 
			
		||||
              v-else
 | 
			
		||||
              class="status-preview status-preview-loading"
 | 
			
		||||
            >
 | 
			
		||||
              <i class="icon-spin4 animate-spin" />
 | 
			
		||||
          <div v-if="showPreview" class="status-preview-container">
 | 
			
		||||
            <status class="status-preview" v-if="preview" :isPreview="true" :statusoid="preview" :compact=true></status>
 | 
			
		||||
            <div class="status-preview status-preview-loading" v-else>
 | 
			
		||||
              <i class="icon-spin4 animate-spin"></i>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="longSubject"
 | 
			
		||||
            class="status-content-wrapper"
 | 
			
		||||
            :class="{ 'tall-status': !showingLongSubject }"
 | 
			
		||||
          >
 | 
			
		||||
            <a
 | 
			
		||||
              v-if="!showingLongSubject"
 | 
			
		||||
              class="tall-status-hider"
 | 
			
		||||
              :class="{ 'tall-status-hider_focused': isFocused }"
 | 
			
		||||
              href="#"
 | 
			
		||||
              @click.prevent="showingLongSubject=true"
 | 
			
		||||
            >{{ $t("general.show_more") }}</a>
 | 
			
		||||
            <div
 | 
			
		||||
              class="status-content media-body"
 | 
			
		||||
              @click.prevent="linkClicked"
 | 
			
		||||
              v-html="contentHtml"
 | 
			
		||||
            />
 | 
			
		||||
            <a
 | 
			
		||||
              v-if="showingLongSubject"
 | 
			
		||||
              href="#"
 | 
			
		||||
              class="status-unhider"
 | 
			
		||||
              @click.prevent="showingLongSubject=false"
 | 
			
		||||
            >{{ $t("general.show_less") }}</a>
 | 
			
		||||
          <div class="status-content-wrapper" :class="{ 'tall-status': !showingLongSubject }" v-if="longSubject">
 | 
			
		||||
            <a class="tall-status-hider" :class="{ 'tall-status-hider_focused': isFocused }" v-if="!showingLongSubject" href="#" @click.prevent="showingLongSubject=true">{{$t("general.show_more")}}</a>
 | 
			
		||||
            <div @click.prevent="linkClicked" class="status-content media-body" v-html="contentHtml"></div>
 | 
			
		||||
            <a v-if="showingLongSubject" href="#" class="status-unhider" @click.prevent="showingLongSubject=false">{{$t("general.show_less")}}</a>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div
 | 
			
		||||
            v-else
 | 
			
		||||
            :class="{'tall-status': hideTallStatus}"
 | 
			
		||||
            class="status-content-wrapper"
 | 
			
		||||
          >
 | 
			
		||||
            <a
 | 
			
		||||
              v-if="hideTallStatus"
 | 
			
		||||
              class="tall-status-hider"
 | 
			
		||||
              :class="{ 'tall-status-hider_focused': isFocused }"
 | 
			
		||||
              href="#"
 | 
			
		||||
              @click.prevent="toggleShowMore"
 | 
			
		||||
            >{{ $t("general.show_more") }}</a>
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="!hideSubjectStatus"
 | 
			
		||||
              class="status-content media-body"
 | 
			
		||||
              @click.prevent="linkClicked"
 | 
			
		||||
              v-html="contentHtml"
 | 
			
		||||
            />
 | 
			
		||||
            <div
 | 
			
		||||
              v-else
 | 
			
		||||
              class="status-content media-body"
 | 
			
		||||
              @click.prevent="linkClicked"
 | 
			
		||||
              v-html="status.summary_html"
 | 
			
		||||
            />
 | 
			
		||||
            <a
 | 
			
		||||
              v-if="hideSubjectStatus"
 | 
			
		||||
              href="#"
 | 
			
		||||
              class="cw-status-hider"
 | 
			
		||||
              @click.prevent="toggleShowMore"
 | 
			
		||||
            >{{ $t("general.show_more") }}</a>
 | 
			
		||||
            <a
 | 
			
		||||
              v-if="showingMore"
 | 
			
		||||
              href="#"
 | 
			
		||||
              class="status-unhider"
 | 
			
		||||
              @click.prevent="toggleShowMore"
 | 
			
		||||
            >{{ $t("general.show_less") }}</a>
 | 
			
		||||
          <div :class="{'tall-status': hideTallStatus}" class="status-content-wrapper" v-else>
 | 
			
		||||
            <a class="tall-status-hider" :class="{ 'tall-status-hider_focused': isFocused }" v-if="hideTallStatus" href="#" @click.prevent="toggleShowMore">{{$t("general.show_more")}}</a>
 | 
			
		||||
            <div @click.prevent="linkClicked" class="status-content media-body" v-html="contentHtml" v-if="!hideSubjectStatus"></div>
 | 
			
		||||
            <div @click.prevent="linkClicked" class="status-content media-body" v-html="status.summary_html" v-else></div>
 | 
			
		||||
            <a v-if="hideSubjectStatus" href="#" class="cw-status-hider" @click.prevent="toggleShowMore">{{$t("general.show_more")}}</a>
 | 
			
		||||
            <a v-if="showingMore" href="#" class="status-unhider" @click.prevent="toggleShowMore">{{$t("general.show_less")}}</a>
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="status.attachments && (!hideSubjectStatus || showingLongSubject)"
 | 
			
		||||
            class="attachments media-body"
 | 
			
		||||
          >
 | 
			
		||||
          <div v-if="status.attachments && (!hideSubjectStatus || showingLongSubject)" class="attachments media-body">
 | 
			
		||||
            <attachment
 | 
			
		||||
              v-for="attachment in nonGalleryAttachments"
 | 
			
		||||
              :key="attachment.id"
 | 
			
		||||
              class="non-gallery"
 | 
			
		||||
              v-for="attachment in nonGalleryAttachments"
 | 
			
		||||
              :size="attachmentSize"
 | 
			
		||||
              :nsfw="nsfwClickthrough"
 | 
			
		||||
              :attachment="attachment"
 | 
			
		||||
              :allow-play="true"
 | 
			
		||||
              :set-media="setMedia()"
 | 
			
		||||
              :allowPlay="true"
 | 
			
		||||
              :setMedia="setMedia()"
 | 
			
		||||
              :key="attachment.id"
 | 
			
		||||
            />
 | 
			
		||||
            <gallery
 | 
			
		||||
              v-if="galleryAttachments.length > 0"
 | 
			
		||||
              :nsfw="nsfwClickthrough"
 | 
			
		||||
              :attachments="galleryAttachments"
 | 
			
		||||
              :set-media="setMedia()"
 | 
			
		||||
              :setMedia="setMedia()"
 | 
			
		||||
            />
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="status.card && !hideSubjectStatus && !noHeading"
 | 
			
		||||
            class="link-preview media-body"
 | 
			
		||||
          >
 | 
			
		||||
            <link-preview
 | 
			
		||||
              :card="status.card"
 | 
			
		||||
              :size="attachmentSize"
 | 
			
		||||
              :nsfw="nsfwClickthrough"
 | 
			
		||||
            />
 | 
			
		||||
          <div v-if="status.card && !hideSubjectStatus && !noHeading" class="link-preview media-body">
 | 
			
		||||
            <link-preview :card="status.card" :size="attachmentSize" :nsfw="nsfwClickthrough" />
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="!noHeading && !isPreview"
 | 
			
		||||
            class="status-actions media-body"
 | 
			
		||||
          >
 | 
			
		||||
          <div v-if="!noHeading && !isPreview" class='status-actions media-body'>
 | 
			
		||||
            <div v-if="loggedIn">
 | 
			
		||||
              <i
 | 
			
		||||
                class="button-icon icon-reply"
 | 
			
		||||
                :title="$t('tool_tip.reply')"
 | 
			
		||||
                :class="{'icon-reply-active': replying}"
 | 
			
		||||
                @click.prevent="toggleReplying"
 | 
			
		||||
              />
 | 
			
		||||
              <span v-if="status.replies_count > 0">{{ status.replies_count }}</span>
 | 
			
		||||
              <i class="button-icon icon-reply" v-on:click.prevent="toggleReplying" :title="$t('tool_tip.reply')" :class="{'icon-reply-active': replying}"></i>
 | 
			
		||||
              <span v-if="status.replies_count > 0">{{status.replies_count}}</span>
 | 
			
		||||
            </div>
 | 
			
		||||
            <retweet-button
 | 
			
		||||
              :visibility="status.visibility"
 | 
			
		||||
              :logged-in="loggedIn"
 | 
			
		||||
              :status="status"
 | 
			
		||||
            />
 | 
			
		||||
            <favorite-button
 | 
			
		||||
              :logged-in="loggedIn"
 | 
			
		||||
              :status="status"
 | 
			
		||||
            />
 | 
			
		||||
            <delete-button :status="status" />
 | 
			
		||||
            <retweet-button :visibility='status.visibility' :loggedIn='loggedIn' :status='status'></retweet-button>
 | 
			
		||||
            <favorite-button :loggedIn='loggedIn' :status='status'></favorite-button>
 | 
			
		||||
            <delete-button :status='status'></delete-button>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="replying"
 | 
			
		||||
        class="container"
 | 
			
		||||
      >
 | 
			
		||||
        <div class="reply-left" />
 | 
			
		||||
        <post-status-form
 | 
			
		||||
          class="reply-body"
 | 
			
		||||
          :reply-to="status.id"
 | 
			
		||||
          :attentions="status.attentions"
 | 
			
		||||
          :replied-user="status.user"
 | 
			
		||||
          :copy-message-scope="status.visibility"
 | 
			
		||||
          :subject="replySubject"
 | 
			
		||||
          @posted="toggleReplying"
 | 
			
		||||
        />
 | 
			
		||||
      <div class="container" v-if="replying">
 | 
			
		||||
        <div class="reply-left"/>
 | 
			
		||||
        <post-status-form class="reply-body" :reply-to="status.id" :attentions="status.attentions" :repliedUser="status.user" :copy-message-scope="status.visibility" :subject="replySubject" v-on:posted="toggleReplying"/>
 | 
			
		||||
      </div>
 | 
			
		||||
    </template>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,19 +1,7 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="still-image"
 | 
			
		||||
    :class="{ animated: animated }"
 | 
			
		||||
  >
 | 
			
		||||
    <canvas
 | 
			
		||||
      v-if="animated"
 | 
			
		||||
      ref="canvas"
 | 
			
		||||
    />
 | 
			
		||||
    <img
 | 
			
		||||
      ref="src"
 | 
			
		||||
      :src="src"
 | 
			
		||||
      :referrerpolicy="referrerpolicy"
 | 
			
		||||
      @load="onLoad"
 | 
			
		||||
      @error="onError"
 | 
			
		||||
    >
 | 
			
		||||
  <div class='still-image' :class='{ animated: animated }' >
 | 
			
		||||
    <canvas ref="canvas" v-if="animated"></canvas>
 | 
			
		||||
    <img ref="src" :src="src" :referrerpolicy="referrerpolicy" v-on:load="onLoad" @error="onError"/>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,101 +1,78 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="panel dummy">
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      <div class="title">
 | 
			
		||||
        {{ $t('settings.style.preview.header') }}
 | 
			
		||||
        <span class="badge badge-notification">
 | 
			
		||||
          99
 | 
			
		||||
        </span>
 | 
			
		||||
      </div>
 | 
			
		||||
      <span class="faint">
 | 
			
		||||
        {{ $t('settings.style.preview.header_faint') }}
 | 
			
		||||
<div class="panel dummy">
 | 
			
		||||
  <div class="panel-heading">
 | 
			
		||||
    <div class="title">
 | 
			
		||||
      {{$t('settings.style.preview.header')}}
 | 
			
		||||
      <span class="badge badge-notification">
 | 
			
		||||
        99
 | 
			
		||||
      </span>
 | 
			
		||||
      <span class="alert error">
 | 
			
		||||
        {{ $t('settings.style.preview.error') }}
 | 
			
		||||
    </div>
 | 
			
		||||
    <span class="faint">
 | 
			
		||||
      {{$t('settings.style.preview.header_faint')}}
 | 
			
		||||
    </span>
 | 
			
		||||
    <span class="alert error">
 | 
			
		||||
      {{$t('settings.style.preview.error')}}
 | 
			
		||||
    </span>
 | 
			
		||||
    <button class="btn">
 | 
			
		||||
      {{$t('settings.style.preview.button')}}
 | 
			
		||||
    </button>
 | 
			
		||||
  </div>
 | 
			
		||||
  <div class="panel-body theme-preview-content">
 | 
			
		||||
    <div class="post">
 | 
			
		||||
      <div class="avatar">
 | 
			
		||||
        ( ͡° ͜ʖ ͡°)
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="content">
 | 
			
		||||
        <h4>
 | 
			
		||||
          {{$t('settings.style.preview.content')}}
 | 
			
		||||
        </h4>
 | 
			
		||||
 | 
			
		||||
        <i18n path="settings.style.preview.text">
 | 
			
		||||
          <code style="font-family: var(--postCodeFont)">
 | 
			
		||||
            {{$t('settings.style.preview.mono')}}
 | 
			
		||||
          </code>
 | 
			
		||||
          <a style="color: var(--link)">
 | 
			
		||||
            {{$t('settings.style.preview.link')}}
 | 
			
		||||
          </a>
 | 
			
		||||
        </i18n>
 | 
			
		||||
 | 
			
		||||
        <div class="icons">
 | 
			
		||||
          <i style="color: var(--cBlue)" class="button-icon icon-reply"/>
 | 
			
		||||
          <i style="color: var(--cGreen)" class="button-icon icon-retweet"/>
 | 
			
		||||
          <i style="color: var(--cOrange)" class="button-icon icon-star"/>
 | 
			
		||||
          <i style="color: var(--cRed)" class="button-icon icon-cancel"/>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <div class="after-post">
 | 
			
		||||
      <div class="avatar-alt">
 | 
			
		||||
        :^)
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="content">
 | 
			
		||||
        <i18n path="settings.style.preview.fine_print" tag="span" class="faint">
 | 
			
		||||
          <a style="color: var(--faintLink)">
 | 
			
		||||
            {{$t('settings.style.preview.faint_link')}}
 | 
			
		||||
          </a>
 | 
			
		||||
        </i18n>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="separator"></div>
 | 
			
		||||
 | 
			
		||||
    <span class="alert error">
 | 
			
		||||
      {{$t('settings.style.preview.error')}}
 | 
			
		||||
    </span>
 | 
			
		||||
    <input :value="$t('settings.style.preview.input')" type="text">
 | 
			
		||||
 | 
			
		||||
    <div class="actions">
 | 
			
		||||
      <span class="checkbox">
 | 
			
		||||
        <input checked="very yes" type="checkbox" id="preview_checkbox">
 | 
			
		||||
        <label for="preview_checkbox">{{$t('settings.style.preview.checkbox')}}</label>
 | 
			
		||||
      </span>
 | 
			
		||||
      <button class="btn">
 | 
			
		||||
        {{ $t('settings.style.preview.button') }}
 | 
			
		||||
        {{$t('settings.style.preview.button')}}
 | 
			
		||||
      </button>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="panel-body theme-preview-content">
 | 
			
		||||
      <div class="post">
 | 
			
		||||
        <div class="avatar">
 | 
			
		||||
          ( ͡° ͜ʖ ͡°)
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="content">
 | 
			
		||||
          <h4>
 | 
			
		||||
            {{ $t('settings.style.preview.content') }}
 | 
			
		||||
          </h4>
 | 
			
		||||
 | 
			
		||||
          <i18n path="settings.style.preview.text">
 | 
			
		||||
            <code style="font-family: var(--postCodeFont)">
 | 
			
		||||
              {{ $t('settings.style.preview.mono') }}
 | 
			
		||||
            </code>
 | 
			
		||||
            <a style="color: var(--link)">
 | 
			
		||||
              {{ $t('settings.style.preview.link') }}
 | 
			
		||||
            </a>
 | 
			
		||||
          </i18n>
 | 
			
		||||
 | 
			
		||||
          <div class="icons">
 | 
			
		||||
            <i
 | 
			
		||||
              style="color: var(--cBlue)"
 | 
			
		||||
              class="button-icon icon-reply"
 | 
			
		||||
            />
 | 
			
		||||
            <i
 | 
			
		||||
              style="color: var(--cGreen)"
 | 
			
		||||
              class="button-icon icon-retweet"
 | 
			
		||||
            />
 | 
			
		||||
            <i
 | 
			
		||||
              style="color: var(--cOrange)"
 | 
			
		||||
              class="button-icon icon-star"
 | 
			
		||||
            />
 | 
			
		||||
            <i
 | 
			
		||||
              style="color: var(--cRed)"
 | 
			
		||||
              class="button-icon icon-cancel"
 | 
			
		||||
            />
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
      <div class="after-post">
 | 
			
		||||
        <div class="avatar-alt">
 | 
			
		||||
          :^)
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="content">
 | 
			
		||||
          <i18n
 | 
			
		||||
            path="settings.style.preview.fine_print"
 | 
			
		||||
            tag="span"
 | 
			
		||||
            class="faint"
 | 
			
		||||
          >
 | 
			
		||||
            <a style="color: var(--faintLink)">
 | 
			
		||||
              {{ $t('settings.style.preview.faint_link') }}
 | 
			
		||||
            </a>
 | 
			
		||||
          </i18n>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="separator" />
 | 
			
		||||
 | 
			
		||||
      <span class="alert error">
 | 
			
		||||
        {{ $t('settings.style.preview.error') }}
 | 
			
		||||
      </span>
 | 
			
		||||
      <input
 | 
			
		||||
        :value="$t('settings.style.preview.input')"
 | 
			
		||||
        type="text"
 | 
			
		||||
      >
 | 
			
		||||
 | 
			
		||||
      <div class="actions">
 | 
			
		||||
        <span class="checkbox">
 | 
			
		||||
          <input
 | 
			
		||||
            id="preview_checkbox"
 | 
			
		||||
            checked="very yes"
 | 
			
		||||
            type="checkbox"
 | 
			
		||||
          >
 | 
			
		||||
          <label for="preview_checkbox">{{ $t('settings.style.preview.checkbox') }}</label>
 | 
			
		||||
        </span>
 | 
			
		||||
        <button class="btn">
 | 
			
		||||
          {{ $t('settings.style.preview.button') }}
 | 
			
		||||
        </button>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,593 +1,274 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="style-switcher">
 | 
			
		||||
    <div class="presets-container">
 | 
			
		||||
      <div class="save-load">
 | 
			
		||||
        <export-import
 | 
			
		||||
          :export-object="exportedTheme"
 | 
			
		||||
          :export-label="$t("settings.export_theme")"
 | 
			
		||||
          :import-label="$t("settings.import_theme")"
 | 
			
		||||
          :import-failed-text="$t("settings.invalid_theme_imported")"
 | 
			
		||||
          :on-import="onImport"
 | 
			
		||||
          :validator="importValidator"
 | 
			
		||||
        >
 | 
			
		||||
          <template slot="before">
 | 
			
		||||
            <div class="presets">
 | 
			
		||||
              {{ $t('settings.presets') }}
 | 
			
		||||
              <label
 | 
			
		||||
                for="preset-switcher"
 | 
			
		||||
                class="select"
 | 
			
		||||
              >
 | 
			
		||||
                <select
 | 
			
		||||
                  id="preset-switcher"
 | 
			
		||||
                  v-model="selected"
 | 
			
		||||
                  class="preset-switcher"
 | 
			
		||||
                >
 | 
			
		||||
                  <option
 | 
			
		||||
                    v-for="style in availableStyles"
 | 
			
		||||
                    :key="style.name"
 | 
			
		||||
                    :value="style"
 | 
			
		||||
                    :style="{
 | 
			
		||||
                      backgroundColor: style[1] || style.theme.colors.bg,
 | 
			
		||||
                      color: style[3] || style.theme.colors.text
 | 
			
		||||
                    }"
 | 
			
		||||
                  >
 | 
			
		||||
                    {{ style[0] || style.name }}
 | 
			
		||||
                  </option>
 | 
			
		||||
                </select>
 | 
			
		||||
                <i class="icon-down-open" />
 | 
			
		||||
              </label>
 | 
			
		||||
            </div>
 | 
			
		||||
          </template>
 | 
			
		||||
        </export-import>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="save-load-options">
 | 
			
		||||
        <span class="keep-option">
 | 
			
		||||
          <input
 | 
			
		||||
            id="keep-color"
 | 
			
		||||
            v-model="keepColor"
 | 
			
		||||
            type="checkbox"
 | 
			
		||||
          >
 | 
			
		||||
          <label for="keep-color">{{ $t('settings.style.switcher.keep_color') }}</label>
 | 
			
		||||
        </span>
 | 
			
		||||
        <span class="keep-option">
 | 
			
		||||
          <input
 | 
			
		||||
            id="keep-shadows"
 | 
			
		||||
            v-model="keepShadows"
 | 
			
		||||
            type="checkbox"
 | 
			
		||||
          >
 | 
			
		||||
          <label for="keep-shadows">{{ $t('settings.style.switcher.keep_shadows') }}</label>
 | 
			
		||||
        </span>
 | 
			
		||||
        <span class="keep-option">
 | 
			
		||||
          <input
 | 
			
		||||
            id="keep-opacity"
 | 
			
		||||
            v-model="keepOpacity"
 | 
			
		||||
            type="checkbox"
 | 
			
		||||
          >
 | 
			
		||||
          <label for="keep-opacity">{{ $t('settings.style.switcher.keep_opacity') }}</label>
 | 
			
		||||
        </span>
 | 
			
		||||
        <span class="keep-option">
 | 
			
		||||
          <input
 | 
			
		||||
            id="keep-roundness"
 | 
			
		||||
            v-model="keepRoundness"
 | 
			
		||||
            type="checkbox"
 | 
			
		||||
          >
 | 
			
		||||
          <label for="keep-roundness">{{ $t('settings.style.switcher.keep_roundness') }}</label>
 | 
			
		||||
        </span>
 | 
			
		||||
        <span class="keep-option">
 | 
			
		||||
          <input
 | 
			
		||||
            id="keep-fonts"
 | 
			
		||||
            v-model="keepFonts"
 | 
			
		||||
            type="checkbox"
 | 
			
		||||
          >
 | 
			
		||||
          <label for="keep-fonts">{{ $t('settings.style.switcher.keep_fonts') }}</label>
 | 
			
		||||
        </span>
 | 
			
		||||
        <p>{{ $t('settings.style.switcher.save_load_hint') }}</p>
 | 
			
		||||
      </div>
 | 
			
		||||
<div class="style-switcher">
 | 
			
		||||
  <div class="presets-container">
 | 
			
		||||
    <div class="save-load">
 | 
			
		||||
      <export-import
 | 
			
		||||
        :exportObject='exportedTheme'
 | 
			
		||||
        :exportLabel='$t("settings.export_theme")'
 | 
			
		||||
        :importLabel='$t("settings.import_theme")'
 | 
			
		||||
        :importFailedText='$t("settings.invalid_theme_imported")'
 | 
			
		||||
        :onImport='onImport'
 | 
			
		||||
        :validator='importValidator'>
 | 
			
		||||
        <template slot="before">
 | 
			
		||||
          <div class="presets">
 | 
			
		||||
            {{$t('settings.presets')}}
 | 
			
		||||
            <label for="preset-switcher" class='select'>
 | 
			
		||||
              <select id="preset-switcher" v-model="selected" class="preset-switcher">
 | 
			
		||||
                <option v-for="style in availableStyles"
 | 
			
		||||
                        :value="style"
 | 
			
		||||
                        :style="{
 | 
			
		||||
                                backgroundColor: style[1] || style.theme.colors.bg,
 | 
			
		||||
                                color: style[3] || style.theme.colors.text
 | 
			
		||||
                                }">
 | 
			
		||||
                  {{style[0] || style.name}}
 | 
			
		||||
                </option>
 | 
			
		||||
              </select>
 | 
			
		||||
              <i class="icon-down-open"/>
 | 
			
		||||
            </label>
 | 
			
		||||
          </div>
 | 
			
		||||
        </template>
 | 
			
		||||
      </export-import>
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <div class="preview-container">
 | 
			
		||||
      <preview :style="previewRules" />
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <keep-alive>
 | 
			
		||||
      <tab-switcher key="style-tweak">
 | 
			
		||||
        <div
 | 
			
		||||
          :label="$t('settings.style.common_colors._tab_label')"
 | 
			
		||||
          class="color-container"
 | 
			
		||||
        >
 | 
			
		||||
          <div class="tab-header">
 | 
			
		||||
            <p>{{ $t('settings.theme_help') }}</p>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn"
 | 
			
		||||
              @click="clearOpacity"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.style.switcher.clear_opacity') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn"
 | 
			
		||||
              @click="clearV1"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.style.switcher.clear_all') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </div>
 | 
			
		||||
          <p>{{ $t('settings.theme_help_v2_1') }}</p>
 | 
			
		||||
          <h4>{{ $t('settings.style.common_colors.main') }}</h4>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="bgColorLocal"
 | 
			
		||||
              name="bgColor"
 | 
			
		||||
              :label="$t('settings.background')"
 | 
			
		||||
            />
 | 
			
		||||
            <OpacityInput
 | 
			
		||||
              v-model="bgOpacityLocal"
 | 
			
		||||
              name="bgOpacity"
 | 
			
		||||
              :fallback="previewTheme.opacity.bg || 1"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="textColorLocal"
 | 
			
		||||
              name="textColor"
 | 
			
		||||
              :label="$t('settings.text')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.bgText" />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="linkColorLocal"
 | 
			
		||||
              name="linkColor"
 | 
			
		||||
              :label="$t('settings.links')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.bgLink" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="fgColorLocal"
 | 
			
		||||
              name="fgColor"
 | 
			
		||||
              :label="$t('settings.foreground')"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="fgTextColorLocal"
 | 
			
		||||
              name="fgTextColor"
 | 
			
		||||
              :label="$t('settings.text')"
 | 
			
		||||
              :fallback="previewTheme.colors.fgText"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="fgLinkColorLocal"
 | 
			
		||||
              name="fgLinkColor"
 | 
			
		||||
              :label="$t('settings.links')"
 | 
			
		||||
              :fallback="previewTheme.colors.fgLink"
 | 
			
		||||
            />
 | 
			
		||||
            <p>{{ $t('settings.style.common_colors.foreground_hint') }}</p>
 | 
			
		||||
          </div>
 | 
			
		||||
          <h4>{{ $t('settings.style.common_colors.rgbo') }}</h4>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="cRedColorLocal"
 | 
			
		||||
              name="cRedColor"
 | 
			
		||||
              :label="$t('settings.cRed')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.bgRed" />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="cBlueColorLocal"
 | 
			
		||||
              name="cBlueColor"
 | 
			
		||||
              :label="$t('settings.cBlue')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.bgBlue" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="cGreenColorLocal"
 | 
			
		||||
              name="cGreenColor"
 | 
			
		||||
              :label="$t('settings.cGreen')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.bgGreen" />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="cOrangeColorLocal"
 | 
			
		||||
              name="cOrangeColor"
 | 
			
		||||
              :label="$t('settings.cOrange')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.bgOrange" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <p>{{ $t('settings.theme_help_v2_2') }}</p>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div
 | 
			
		||||
          :label="$t('settings.style.advanced_colors._tab_label')"
 | 
			
		||||
          class="color-container"
 | 
			
		||||
        >
 | 
			
		||||
          <div class="tab-header">
 | 
			
		||||
            <p>{{ $t('settings.theme_help') }}</p>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn"
 | 
			
		||||
              @click="clearOpacity"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.style.switcher.clear_opacity') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn"
 | 
			
		||||
              @click="clearV1"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.style.switcher.clear_all') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <h4>{{ $t('settings.style.advanced_colors.alert') }}</h4>
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="alertErrorColorLocal"
 | 
			
		||||
              name="alertError"
 | 
			
		||||
              :label="$t('settings.style.advanced_colors.alert_error')"
 | 
			
		||||
              :fallback="previewTheme.colors.alertError"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.alertError" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <h4>{{ $t('settings.style.advanced_colors.badge') }}</h4>
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="badgeNotificationColorLocal"
 | 
			
		||||
              name="badgeNotification"
 | 
			
		||||
              :label="$t('settings.style.advanced_colors.badge_notification')"
 | 
			
		||||
              :fallback="previewTheme.colors.badgeNotification"
 | 
			
		||||
            />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <h4>{{ $t('settings.style.advanced_colors.panel_header') }}</h4>
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="panelColorLocal"
 | 
			
		||||
              name="panelColor"
 | 
			
		||||
              :fallback="fgColorLocal"
 | 
			
		||||
              :label="$t('settings.background')"
 | 
			
		||||
            />
 | 
			
		||||
            <OpacityInput
 | 
			
		||||
              v-model="panelOpacityLocal"
 | 
			
		||||
              name="panelOpacity"
 | 
			
		||||
              :fallback="previewTheme.opacity.panel || 1"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="panelTextColorLocal"
 | 
			
		||||
              name="panelTextColor"
 | 
			
		||||
              :fallback="previewTheme.colors.panelText"
 | 
			
		||||
              :label="$t('settings.text')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio
 | 
			
		||||
              :contrast="previewContrast.panelText"
 | 
			
		||||
              large="1"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="panelLinkColorLocal"
 | 
			
		||||
              name="panelLinkColor"
 | 
			
		||||
              :fallback="previewTheme.colors.panelLink"
 | 
			
		||||
              :label="$t('settings.links')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio
 | 
			
		||||
              :contrast="previewContrast.panelLink"
 | 
			
		||||
              large="1"
 | 
			
		||||
            />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <h4>{{ $t('settings.style.advanced_colors.top_bar') }}</h4>
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="topBarColorLocal"
 | 
			
		||||
              name="topBarColor"
 | 
			
		||||
              :fallback="fgColorLocal"
 | 
			
		||||
              :label="$t('settings.background')"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="topBarTextColorLocal"
 | 
			
		||||
              name="topBarTextColor"
 | 
			
		||||
              :fallback="previewTheme.colors.topBarText"
 | 
			
		||||
              :label="$t('settings.text')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.topBarText" />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="topBarLinkColorLocal"
 | 
			
		||||
              name="topBarLinkColor"
 | 
			
		||||
              :fallback="previewTheme.colors.topBarLink"
 | 
			
		||||
              :label="$t('settings.links')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.topBarLink" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <h4>{{ $t('settings.style.advanced_colors.inputs') }}</h4>
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="inputColorLocal"
 | 
			
		||||
              name="inputColor"
 | 
			
		||||
              :fallback="fgColorLocal"
 | 
			
		||||
              :label="$t('settings.background')"
 | 
			
		||||
            />
 | 
			
		||||
            <OpacityInput
 | 
			
		||||
              v-model="inputOpacityLocal"
 | 
			
		||||
              name="inputOpacity"
 | 
			
		||||
              :fallback="previewTheme.opacity.input || 1"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="inputTextColorLocal"
 | 
			
		||||
              name="inputTextColor"
 | 
			
		||||
              :fallback="previewTheme.colors.inputText"
 | 
			
		||||
              :label="$t('settings.text')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.inputText" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <h4>{{ $t('settings.style.advanced_colors.buttons') }}</h4>
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="btnColorLocal"
 | 
			
		||||
              name="btnColor"
 | 
			
		||||
              :fallback="fgColorLocal"
 | 
			
		||||
              :label="$t('settings.background')"
 | 
			
		||||
            />
 | 
			
		||||
            <OpacityInput
 | 
			
		||||
              v-model="btnOpacityLocal"
 | 
			
		||||
              name="btnOpacity"
 | 
			
		||||
              :fallback="previewTheme.opacity.btn || 1"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="btnTextColorLocal"
 | 
			
		||||
              name="btnTextColor"
 | 
			
		||||
              :fallback="previewTheme.colors.btnText"
 | 
			
		||||
              :label="$t('settings.text')"
 | 
			
		||||
            />
 | 
			
		||||
            <ContrastRatio :contrast="previewContrast.btnText" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <h4>{{ $t('settings.style.advanced_colors.borders') }}</h4>
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="borderColorLocal"
 | 
			
		||||
              name="borderColor"
 | 
			
		||||
              :fallback="previewTheme.colors.border"
 | 
			
		||||
              :label="$t('settings.style.common.color')"
 | 
			
		||||
            />
 | 
			
		||||
            <OpacityInput
 | 
			
		||||
              v-model="borderOpacityLocal"
 | 
			
		||||
              name="borderOpacity"
 | 
			
		||||
              :fallback="previewTheme.opacity.border || 1"
 | 
			
		||||
            />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="color-item">
 | 
			
		||||
            <h4>{{ $t('settings.style.advanced_colors.faint_text') }}</h4>
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="faintColorLocal"
 | 
			
		||||
              name="faintColor"
 | 
			
		||||
              :fallback="previewTheme.colors.faint || 1"
 | 
			
		||||
              :label="$t('settings.text')"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="faintLinkColorLocal"
 | 
			
		||||
              name="faintLinkColor"
 | 
			
		||||
              :fallback="previewTheme.colors.faintLink"
 | 
			
		||||
              :label="$t('settings.links')"
 | 
			
		||||
            />
 | 
			
		||||
            <ColorInput
 | 
			
		||||
              v-model="panelFaintColorLocal"
 | 
			
		||||
              name="panelFaintColor"
 | 
			
		||||
              :fallback="previewTheme.colors.panelFaint"
 | 
			
		||||
              :label="$t('settings.style.advanced_colors.panel_header')"
 | 
			
		||||
            />
 | 
			
		||||
            <OpacityInput
 | 
			
		||||
              v-model="faintOpacityLocal"
 | 
			
		||||
              name="faintOpacity"
 | 
			
		||||
              :fallback="previewTheme.opacity.faint || 0.5"
 | 
			
		||||
            />
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div
 | 
			
		||||
          :label="$t('settings.style.radii._tab_label')"
 | 
			
		||||
          class="radius-container"
 | 
			
		||||
        >
 | 
			
		||||
          <div class="tab-header">
 | 
			
		||||
            <p>{{ $t('settings.radii_help') }}</p>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn"
 | 
			
		||||
              @click="clearRoundness"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.style.switcher.clear_all') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </div>
 | 
			
		||||
          <RangeInput
 | 
			
		||||
            v-model="btnRadiusLocal"
 | 
			
		||||
            name="btnRadius"
 | 
			
		||||
            :label="$t('settings.btnRadius')"
 | 
			
		||||
            :fallback="previewTheme.radii.btn"
 | 
			
		||||
            max="16"
 | 
			
		||||
            hard-min="0"
 | 
			
		||||
          />
 | 
			
		||||
          <RangeInput
 | 
			
		||||
            v-model="inputRadiusLocal"
 | 
			
		||||
            name="inputRadius"
 | 
			
		||||
            :label="$t('settings.inputRadius')"
 | 
			
		||||
            :fallback="previewTheme.radii.input"
 | 
			
		||||
            max="9"
 | 
			
		||||
            hard-min="0"
 | 
			
		||||
          />
 | 
			
		||||
          <RangeInput
 | 
			
		||||
            v-model="checkboxRadiusLocal"
 | 
			
		||||
            name="checkboxRadius"
 | 
			
		||||
            :label="$t('settings.checkboxRadius')"
 | 
			
		||||
            :fallback="previewTheme.radii.checkbox"
 | 
			
		||||
            max="16"
 | 
			
		||||
            hard-min="0"
 | 
			
		||||
          />
 | 
			
		||||
          <RangeInput
 | 
			
		||||
            v-model="panelRadiusLocal"
 | 
			
		||||
            name="panelRadius"
 | 
			
		||||
            :label="$t('settings.panelRadius')"
 | 
			
		||||
            :fallback="previewTheme.radii.panel"
 | 
			
		||||
            max="50"
 | 
			
		||||
            hard-min="0"
 | 
			
		||||
          />
 | 
			
		||||
          <RangeInput
 | 
			
		||||
            v-model="avatarRadiusLocal"
 | 
			
		||||
            name="avatarRadius"
 | 
			
		||||
            :label="$t('settings.avatarRadius')"
 | 
			
		||||
            :fallback="previewTheme.radii.avatar"
 | 
			
		||||
            max="28"
 | 
			
		||||
            hard-min="0"
 | 
			
		||||
          />
 | 
			
		||||
          <RangeInput
 | 
			
		||||
            v-model="avatarAltRadiusLocal"
 | 
			
		||||
            name="avatarAltRadius"
 | 
			
		||||
            :label="$t('settings.avatarAltRadius')"
 | 
			
		||||
            :fallback="previewTheme.radii.avatarAlt"
 | 
			
		||||
            max="28"
 | 
			
		||||
            hard-min="0"
 | 
			
		||||
          />
 | 
			
		||||
          <RangeInput
 | 
			
		||||
            v-model="attachmentRadiusLocal"
 | 
			
		||||
            name="attachmentRadius"
 | 
			
		||||
            :label="$t('settings.attachmentRadius')"
 | 
			
		||||
            :fallback="previewTheme.radii.attachment"
 | 
			
		||||
            max="50"
 | 
			
		||||
            hard-min="0"
 | 
			
		||||
          />
 | 
			
		||||
          <RangeInput
 | 
			
		||||
            v-model="tooltipRadiusLocal"
 | 
			
		||||
            name="tooltipRadius"
 | 
			
		||||
            :label="$t('settings.tooltipRadius')"
 | 
			
		||||
            :fallback="previewTheme.radii.tooltip"
 | 
			
		||||
            max="50"
 | 
			
		||||
            hard-min="0"
 | 
			
		||||
          />
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div
 | 
			
		||||
          :label="$t('settings.style.shadows._tab_label')"
 | 
			
		||||
          class="shadow-container"
 | 
			
		||||
        >
 | 
			
		||||
          <div class="tab-header shadow-selector">
 | 
			
		||||
            <div class="select-container">
 | 
			
		||||
              {{ $t('settings.style.shadows.component') }}
 | 
			
		||||
              <label
 | 
			
		||||
                for="shadow-switcher"
 | 
			
		||||
                class="select"
 | 
			
		||||
              >
 | 
			
		||||
                <select
 | 
			
		||||
                  id="shadow-switcher"
 | 
			
		||||
                  v-model="shadowSelected"
 | 
			
		||||
                  class="shadow-switcher"
 | 
			
		||||
                >
 | 
			
		||||
                  <option
 | 
			
		||||
                    v-for="shadow in shadowsAvailable"
 | 
			
		||||
                    :key="shadow"
 | 
			
		||||
                    :value="shadow"
 | 
			
		||||
                  >
 | 
			
		||||
                    {{ $t('settings.style.shadows.components.' + shadow) }}
 | 
			
		||||
                  </option>
 | 
			
		||||
                </select>
 | 
			
		||||
                <i class="icon-down-open" />
 | 
			
		||||
              </label>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="override">
 | 
			
		||||
              <label
 | 
			
		||||
                for="override"
 | 
			
		||||
                class="label"
 | 
			
		||||
              >
 | 
			
		||||
                {{ $t('settings.style.shadows.override') }}
 | 
			
		||||
              </label>
 | 
			
		||||
              <input
 | 
			
		||||
                id="override"
 | 
			
		||||
                v-model="currentShadowOverriden"
 | 
			
		||||
                name="override"
 | 
			
		||||
                class="input-override"
 | 
			
		||||
                type="checkbox"
 | 
			
		||||
              >
 | 
			
		||||
              <label
 | 
			
		||||
                class="checkbox-label"
 | 
			
		||||
                for="override"
 | 
			
		||||
              />
 | 
			
		||||
            </div>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn"
 | 
			
		||||
              @click="clearShadows"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.style.switcher.clear_all') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </div>
 | 
			
		||||
          <shadow-control
 | 
			
		||||
            v-model="currentShadow"
 | 
			
		||||
            :ready="!!currentShadowFallback"
 | 
			
		||||
            :fallback="currentShadowFallback"
 | 
			
		||||
          />
 | 
			
		||||
          <div v-if="shadowSelected === 'avatar' || shadowSelected === 'avatarStatus'">
 | 
			
		||||
            <i18n
 | 
			
		||||
              path="settings.style.shadows.filter_hint.always_drop_shadow"
 | 
			
		||||
              tag="p"
 | 
			
		||||
            >
 | 
			
		||||
              <code>filter: drop-shadow()</code>
 | 
			
		||||
            </i18n>
 | 
			
		||||
            <p>{{ $t('settings.style.shadows.filter_hint.avatar_inset') }}</p>
 | 
			
		||||
            <i18n
 | 
			
		||||
              path="settings.style.shadows.filter_hint.drop_shadow_syntax"
 | 
			
		||||
              tag="p"
 | 
			
		||||
            >
 | 
			
		||||
              <code>drop-shadow</code>
 | 
			
		||||
              <code>spread-radius</code>
 | 
			
		||||
              <code>inset</code>
 | 
			
		||||
            </i18n>
 | 
			
		||||
            <i18n
 | 
			
		||||
              path="settings.style.shadows.filter_hint.inset_classic"
 | 
			
		||||
              tag="p"
 | 
			
		||||
            >
 | 
			
		||||
              <code>box-shadow</code>
 | 
			
		||||
            </i18n>
 | 
			
		||||
            <p>{{ $t('settings.style.shadows.filter_hint.spread_zero') }}</p>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div
 | 
			
		||||
          :label="$t('settings.style.fonts._tab_label')"
 | 
			
		||||
          class="fonts-container"
 | 
			
		||||
        >
 | 
			
		||||
          <div class="tab-header">
 | 
			
		||||
            <p>{{ $t('settings.style.fonts.help') }}</p>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn"
 | 
			
		||||
              @click="clearFonts"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.style.switcher.clear_all') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </div>
 | 
			
		||||
          <FontControl
 | 
			
		||||
            v-model="fontsLocal.interface"
 | 
			
		||||
            name="ui"
 | 
			
		||||
            :label="$t('settings.style.fonts.components.interface')"
 | 
			
		||||
            :fallback="previewTheme.fonts.interface"
 | 
			
		||||
            no-inherit="1"
 | 
			
		||||
          />
 | 
			
		||||
          <FontControl
 | 
			
		||||
            v-model="fontsLocal.input"
 | 
			
		||||
            name="input"
 | 
			
		||||
            :label="$t('settings.style.fonts.components.input')"
 | 
			
		||||
            :fallback="previewTheme.fonts.input"
 | 
			
		||||
          />
 | 
			
		||||
          <FontControl
 | 
			
		||||
            v-model="fontsLocal.post"
 | 
			
		||||
            name="post"
 | 
			
		||||
            :label="$t('settings.style.fonts.components.post')"
 | 
			
		||||
            :fallback="previewTheme.fonts.post"
 | 
			
		||||
          />
 | 
			
		||||
          <FontControl
 | 
			
		||||
            v-model="fontsLocal.postCode"
 | 
			
		||||
            name="postCode"
 | 
			
		||||
            :label="$t('settings.style.fonts.components.postCode')"
 | 
			
		||||
            :fallback="previewTheme.fonts.postCode"
 | 
			
		||||
          />
 | 
			
		||||
        </div>
 | 
			
		||||
      </tab-switcher>
 | 
			
		||||
    </keep-alive>
 | 
			
		||||
 | 
			
		||||
    <div class="apply-container">
 | 
			
		||||
      <button
 | 
			
		||||
        class="btn submit"
 | 
			
		||||
        :disabled="!themeValid"
 | 
			
		||||
        @click="setCustomTheme"
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('general.apply') }}
 | 
			
		||||
      </button>
 | 
			
		||||
      <button
 | 
			
		||||
        class="btn"
 | 
			
		||||
        @click="clearAll"
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('settings.style.switcher.reset') }}
 | 
			
		||||
      </button>
 | 
			
		||||
    <div class="save-load-options">
 | 
			
		||||
      <span class="keep-option">
 | 
			
		||||
        <input
 | 
			
		||||
          id="keep-color"
 | 
			
		||||
          type="checkbox"
 | 
			
		||||
          v-model="keepColor">
 | 
			
		||||
        <label for="keep-color">{{$t('settings.style.switcher.keep_color')}}</label>
 | 
			
		||||
      </span>
 | 
			
		||||
      <span class="keep-option">
 | 
			
		||||
        <input
 | 
			
		||||
          id="keep-shadows"
 | 
			
		||||
          type="checkbox"
 | 
			
		||||
          v-model="keepShadows">
 | 
			
		||||
        <label for="keep-shadows">{{$t('settings.style.switcher.keep_shadows')}}</label>
 | 
			
		||||
      </span>
 | 
			
		||||
      <span class="keep-option">
 | 
			
		||||
        <input
 | 
			
		||||
          id="keep-opacity"
 | 
			
		||||
          type="checkbox"
 | 
			
		||||
          v-model="keepOpacity">
 | 
			
		||||
        <label for="keep-opacity">{{$t('settings.style.switcher.keep_opacity')}}</label>
 | 
			
		||||
      </span>
 | 
			
		||||
      <span class="keep-option">
 | 
			
		||||
        <input
 | 
			
		||||
          id="keep-roundness"
 | 
			
		||||
          type="checkbox"
 | 
			
		||||
          v-model="keepRoundness">
 | 
			
		||||
        <label for="keep-roundness">{{$t('settings.style.switcher.keep_roundness')}}</label>
 | 
			
		||||
      </span>
 | 
			
		||||
      <span class="keep-option">
 | 
			
		||||
        <input
 | 
			
		||||
          id="keep-fonts"
 | 
			
		||||
          type="checkbox"
 | 
			
		||||
          v-model="keepFonts">
 | 
			
		||||
        <label for="keep-fonts">{{$t('settings.style.switcher.keep_fonts')}}</label>
 | 
			
		||||
      </span>
 | 
			
		||||
      <p>{{$t('settings.style.switcher.save_load_hint')}}</p>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
 | 
			
		||||
  <div class="preview-container">
 | 
			
		||||
    <preview :style="previewRules"/>
 | 
			
		||||
  </div>
 | 
			
		||||
 | 
			
		||||
  <keep-alive>
 | 
			
		||||
    <tab-switcher key="style-tweak">
 | 
			
		||||
      <div :label="$t('settings.style.common_colors._tab_label')" class="color-container">
 | 
			
		||||
        <div class="tab-header">
 | 
			
		||||
          <p>{{$t('settings.theme_help')}}</p>
 | 
			
		||||
          <button class="btn" @click="clearOpacity">{{$t('settings.style.switcher.clear_opacity')}}</button>
 | 
			
		||||
          <button class="btn" @click="clearV1">{{$t('settings.style.switcher.clear_all')}}</button>
 | 
			
		||||
        </div>
 | 
			
		||||
        <p>{{$t('settings.theme_help_v2_1')}}</p>
 | 
			
		||||
        <h4>{{ $t('settings.style.common_colors.main') }}</h4>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <ColorInput name="bgColor" v-model="bgColorLocal" :label="$t('settings.background')"/>
 | 
			
		||||
          <OpacityInput name="bgOpacity" v-model="bgOpacityLocal" :fallback="previewTheme.opacity.bg || 1"/>
 | 
			
		||||
          <ColorInput name="textColor" v-model="textColorLocal" :label="$t('settings.text')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.bgText"/>
 | 
			
		||||
          <ColorInput name="linkColor" v-model="linkColorLocal" :label="$t('settings.links')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.bgLink"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <ColorInput name="fgColor" v-model="fgColorLocal" :label="$t('settings.foreground')"/>
 | 
			
		||||
          <ColorInput name="fgTextColor" v-model="fgTextColorLocal" :label="$t('settings.text')" :fallback="previewTheme.colors.fgText"/>
 | 
			
		||||
          <ColorInput name="fgLinkColor" v-model="fgLinkColorLocal" :label="$t('settings.links')" :fallback="previewTheme.colors.fgLink"/>
 | 
			
		||||
          <p>{{ $t('settings.style.common_colors.foreground_hint') }}</p>
 | 
			
		||||
        </div>
 | 
			
		||||
        <h4>{{ $t('settings.style.common_colors.rgbo') }}</h4>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <ColorInput name="cRedColor" v-model="cRedColorLocal" :label="$t('settings.cRed')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.bgRed"/>
 | 
			
		||||
          <ColorInput name="cBlueColor" v-model="cBlueColorLocal" :label="$t('settings.cBlue')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.bgBlue"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <ColorInput name="cGreenColor" v-model="cGreenColorLocal" :label="$t('settings.cGreen')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.bgGreen"/>
 | 
			
		||||
          <ColorInput name="cOrangeColor" v-model="cOrangeColorLocal" :label="$t('settings.cOrange')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.bgOrange"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <p>{{$t('settings.theme_help_v2_2')}}</p>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
      <div :label="$t('settings.style.advanced_colors._tab_label')" class="color-container">
 | 
			
		||||
        <div class="tab-header">
 | 
			
		||||
          <p>{{$t('settings.theme_help')}}</p>
 | 
			
		||||
          <button class="btn" @click="clearOpacity">{{$t('settings.style.switcher.clear_opacity')}}</button>
 | 
			
		||||
          <button class="btn" @click="clearV1">{{$t('settings.style.switcher.clear_all')}}</button>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <h4>{{ $t('settings.style.advanced_colors.alert') }}</h4>
 | 
			
		||||
          <ColorInput name="alertError" v-model="alertErrorColorLocal" :label="$t('settings.style.advanced_colors.alert_error')" :fallback="previewTheme.colors.alertError"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.alertError"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <h4>{{ $t('settings.style.advanced_colors.badge') }}</h4>
 | 
			
		||||
          <ColorInput name="badgeNotification" v-model="badgeNotificationColorLocal" :label="$t('settings.style.advanced_colors.badge_notification')" :fallback="previewTheme.colors.badgeNotification"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <h4>{{ $t('settings.style.advanced_colors.panel_header') }}</h4>
 | 
			
		||||
          <ColorInput name="panelColor" v-model="panelColorLocal" :fallback="fgColorLocal" :label="$t('settings.background')"/>
 | 
			
		||||
          <OpacityInput name="panelOpacity" v-model="panelOpacityLocal" :fallback="previewTheme.opacity.panel || 1"/>
 | 
			
		||||
          <ColorInput name="panelTextColor" v-model="panelTextColorLocal" :fallback="previewTheme.colors.panelText" :label="$t('settings.text')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.panelText" large="1"/>
 | 
			
		||||
          <ColorInput name="panelLinkColor" v-model="panelLinkColorLocal" :fallback="previewTheme.colors.panelLink" :label="$t('settings.links')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.panelLink" large="1"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <h4>{{ $t('settings.style.advanced_colors.top_bar') }}</h4>
 | 
			
		||||
          <ColorInput name="topBarColor" v-model="topBarColorLocal" :fallback="fgColorLocal" :label="$t('settings.background')"/>
 | 
			
		||||
          <ColorInput name="topBarTextColor" v-model="topBarTextColorLocal" :fallback="previewTheme.colors.topBarText" :label="$t('settings.text')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.topBarText"/>
 | 
			
		||||
          <ColorInput name="topBarLinkColor" v-model="topBarLinkColorLocal" :fallback="previewTheme.colors.topBarLink" :label="$t('settings.links')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.topBarLink"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <h4>{{ $t('settings.style.advanced_colors.inputs') }}</h4>
 | 
			
		||||
          <ColorInput name="inputColor" v-model="inputColorLocal" :fallback="fgColorLocal" :label="$t('settings.background')"/>
 | 
			
		||||
          <OpacityInput name="inputOpacity" v-model="inputOpacityLocal" :fallback="previewTheme.opacity.input || 1"/>
 | 
			
		||||
          <ColorInput name="inputTextColor" v-model="inputTextColorLocal" :fallback="previewTheme.colors.inputText" :label="$t('settings.text')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.inputText"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <h4>{{ $t('settings.style.advanced_colors.buttons') }}</h4>
 | 
			
		||||
          <ColorInput name="btnColor" v-model="btnColorLocal" :fallback="fgColorLocal" :label="$t('settings.background')"/>
 | 
			
		||||
          <OpacityInput name="btnOpacity" v-model="btnOpacityLocal" :fallback="previewTheme.opacity.btn || 1"/>
 | 
			
		||||
          <ColorInput name="btnTextColor" v-model="btnTextColorLocal" :fallback="previewTheme.colors.btnText" :label="$t('settings.text')"/>
 | 
			
		||||
          <ContrastRatio :contrast="previewContrast.btnText"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <h4>{{ $t('settings.style.advanced_colors.borders') }}</h4>
 | 
			
		||||
          <ColorInput name="borderColor" v-model="borderColorLocal" :fallback="previewTheme.colors.border" :label="$t('settings.style.common.color')"/>
 | 
			
		||||
          <OpacityInput name="borderOpacity" v-model="borderOpacityLocal" :fallback="previewTheme.opacity.border || 1"/>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="color-item">
 | 
			
		||||
          <h4>{{ $t('settings.style.advanced_colors.faint_text') }}</h4>
 | 
			
		||||
          <ColorInput name="faintColor" v-model="faintColorLocal" :fallback="previewTheme.colors.faint || 1" :label="$t('settings.text')"/>
 | 
			
		||||
          <ColorInput name="faintLinkColor" v-model="faintLinkColorLocal" :fallback="previewTheme.colors.faintLink" :label="$t('settings.links')"/>
 | 
			
		||||
          <ColorInput name="panelFaintColor" v-model="panelFaintColorLocal" :fallback="previewTheme.colors.panelFaint" :label="$t('settings.style.advanced_colors.panel_header')"/>
 | 
			
		||||
          <OpacityInput name="faintOpacity" v-model="faintOpacityLocal" :fallback="previewTheme.opacity.faint || 0.5"/>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
      <div :label="$t('settings.style.radii._tab_label')" class="radius-container">
 | 
			
		||||
        <div class="tab-header">
 | 
			
		||||
          <p>{{$t('settings.radii_help')}}</p>
 | 
			
		||||
          <button class="btn" @click="clearRoundness">{{$t('settings.style.switcher.clear_all')}}</button>
 | 
			
		||||
        </div>
 | 
			
		||||
        <RangeInput name="btnRadius" :label="$t('settings.btnRadius')" v-model="btnRadiusLocal" :fallback="previewTheme.radii.btn" max="16" hardMin="0"/>
 | 
			
		||||
        <RangeInput name="inputRadius" :label="$t('settings.inputRadius')" v-model="inputRadiusLocal" :fallback="previewTheme.radii.input" max="9" hardMin="0"/>
 | 
			
		||||
        <RangeInput name="checkboxRadius" :label="$t('settings.checkboxRadius')" v-model="checkboxRadiusLocal" :fallback="previewTheme.radii.checkbox" max="16" hardMin="0"/>
 | 
			
		||||
        <RangeInput name="panelRadius" :label="$t('settings.panelRadius')" v-model="panelRadiusLocal" :fallback="previewTheme.radii.panel" max="50" hardMin="0"/>
 | 
			
		||||
        <RangeInput name="avatarRadius" :label="$t('settings.avatarRadius')" v-model="avatarRadiusLocal" :fallback="previewTheme.radii.avatar" max="28" hardMin="0"/>
 | 
			
		||||
        <RangeInput name="avatarAltRadius" :label="$t('settings.avatarAltRadius')" v-model="avatarAltRadiusLocal" :fallback="previewTheme.radii.avatarAlt" max="28" hardMin="0"/>
 | 
			
		||||
        <RangeInput name="attachmentRadius" :label="$t('settings.attachmentRadius')" v-model="attachmentRadiusLocal" :fallback="previewTheme.radii.attachment" max="50" hardMin="0"/>
 | 
			
		||||
        <RangeInput name="tooltipRadius" :label="$t('settings.tooltipRadius')" v-model="tooltipRadiusLocal" :fallback="previewTheme.radii.tooltip" max="50" hardMin="0"/>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
      <div :label="$t('settings.style.shadows._tab_label')" class="shadow-container">
 | 
			
		||||
        <div class="tab-header shadow-selector">
 | 
			
		||||
          <div class="select-container">
 | 
			
		||||
            {{$t('settings.style.shadows.component')}}
 | 
			
		||||
            <label for="shadow-switcher" class="select">
 | 
			
		||||
              <select id="shadow-switcher" v-model="shadowSelected" class="shadow-switcher">
 | 
			
		||||
                <option v-for="shadow in shadowsAvailable"
 | 
			
		||||
                        :value="shadow">
 | 
			
		||||
                  {{$t('settings.style.shadows.components.' + shadow)}}
 | 
			
		||||
                </option>
 | 
			
		||||
              </select>
 | 
			
		||||
              <i class="icon-down-open"/>
 | 
			
		||||
            </label>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="override">
 | 
			
		||||
            <label for="override" class="label">
 | 
			
		||||
              {{$t('settings.style.shadows.override')}}
 | 
			
		||||
            </label>
 | 
			
		||||
            <input
 | 
			
		||||
              v-model="currentShadowOverriden"
 | 
			
		||||
              name="override"
 | 
			
		||||
              id="override"
 | 
			
		||||
              class="input-override"
 | 
			
		||||
              type="checkbox">
 | 
			
		||||
            <label class="checkbox-label" for="override"></label>
 | 
			
		||||
          </div>
 | 
			
		||||
          <button class="btn" @click="clearShadows">{{$t('settings.style.switcher.clear_all')}}</button>
 | 
			
		||||
        </div>
 | 
			
		||||
        <shadow-control :ready="!!currentShadowFallback" :fallback="currentShadowFallback" v-model="currentShadow"/>
 | 
			
		||||
        <div v-if="shadowSelected === 'avatar' || shadowSelected === 'avatarStatus'">
 | 
			
		||||
          <i18n path="settings.style.shadows.filter_hint.always_drop_shadow" tag="p">
 | 
			
		||||
            <code>filter: drop-shadow()</code>
 | 
			
		||||
          </i18n>
 | 
			
		||||
          <p>{{$t('settings.style.shadows.filter_hint.avatar_inset')}}</p>
 | 
			
		||||
          <i18n path="settings.style.shadows.filter_hint.drop_shadow_syntax" tag="p">
 | 
			
		||||
            <code>drop-shadow</code>
 | 
			
		||||
            <code>spread-radius</code>
 | 
			
		||||
            <code>inset</code>
 | 
			
		||||
          </i18n>
 | 
			
		||||
          <i18n path="settings.style.shadows.filter_hint.inset_classic" tag="p">
 | 
			
		||||
            <code>box-shadow</code>
 | 
			
		||||
          </i18n>
 | 
			
		||||
          <p>{{$t('settings.style.shadows.filter_hint.spread_zero')}}</p>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
      <div :label="$t('settings.style.fonts._tab_label')" class="fonts-container">
 | 
			
		||||
        <div class="tab-header">
 | 
			
		||||
          <p>{{$t('settings.style.fonts.help')}}</p>
 | 
			
		||||
          <button class="btn" @click="clearFonts">{{$t('settings.style.switcher.clear_all')}}</button>
 | 
			
		||||
        </div>
 | 
			
		||||
        <FontControl
 | 
			
		||||
          name="ui"
 | 
			
		||||
          v-model="fontsLocal.interface"
 | 
			
		||||
          :label="$t('settings.style.fonts.components.interface')"
 | 
			
		||||
          :fallback="previewTheme.fonts.interface"
 | 
			
		||||
          no-inherit="1"/>
 | 
			
		||||
        <FontControl
 | 
			
		||||
          name="input"
 | 
			
		||||
          v-model="fontsLocal.input"
 | 
			
		||||
          :label="$t('settings.style.fonts.components.input')"
 | 
			
		||||
          :fallback="previewTheme.fonts.input"/>
 | 
			
		||||
        <FontControl
 | 
			
		||||
          name="post"
 | 
			
		||||
          v-model="fontsLocal.post"
 | 
			
		||||
          :label="$t('settings.style.fonts.components.post')"
 | 
			
		||||
          :fallback="previewTheme.fonts.post"/>
 | 
			
		||||
        <FontControl
 | 
			
		||||
          name="postCode"
 | 
			
		||||
          v-model="fontsLocal.postCode"
 | 
			
		||||
          :label="$t('settings.style.fonts.components.postCode')"
 | 
			
		||||
          :fallback="previewTheme.fonts.postCode"/>
 | 
			
		||||
      </div>
 | 
			
		||||
    </tab-switcher>
 | 
			
		||||
  </keep-alive>
 | 
			
		||||
 | 
			
		||||
  <div class="apply-container">
 | 
			
		||||
    <button class="btn submit" :disabled="!themeValid" @click="setCustomTheme">{{$t('general.apply')}}</button>
 | 
			
		||||
    <button class="btn" @click="clearAll">{{$t('settings.style.switcher.reset')}}</button>
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./style_switcher.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -10,12 +10,6 @@ export default Vue.component('tab-switcher', {
 | 
			
		|||
      active: this.$slots.default.findIndex(_ => _.tag)
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
  beforeUpdate () {
 | 
			
		||||
    const currentSlot = this.$slots.default[this.active]
 | 
			
		||||
    if (!currentSlot.tag) {
 | 
			
		||||
      this.active = this.$slots.default.findIndex(_ => _.tag)
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
  methods: {
 | 
			
		||||
    activateTab (index) {
 | 
			
		||||
      return () => {
 | 
			
		||||
| 
						 | 
				
			
			@ -23,24 +17,30 @@ export default Vue.component('tab-switcher', {
 | 
			
		|||
      }
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
  beforeUpdate () {
 | 
			
		||||
    const currentSlot = this.$slots.default[this.active]
 | 
			
		||||
    if (!currentSlot.tag) {
 | 
			
		||||
      this.active = this.$slots.default.findIndex(_ => _.tag)
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
  render (h) {
 | 
			
		||||
    const tabs = this.$slots.default
 | 
			
		||||
      .map((slot, index) => {
 | 
			
		||||
        if (!slot.tag) return
 | 
			
		||||
        const classesTab = ['tab']
 | 
			
		||||
        const classesWrapper = ['tab-wrapper']
 | 
			
		||||
          .map((slot, index) => {
 | 
			
		||||
            if (!slot.tag) return
 | 
			
		||||
            const classesTab = ['tab']
 | 
			
		||||
            const classesWrapper = ['tab-wrapper']
 | 
			
		||||
 | 
			
		||||
        if (index === this.active) {
 | 
			
		||||
          classesTab.push('active')
 | 
			
		||||
          classesWrapper.push('active')
 | 
			
		||||
        }
 | 
			
		||||
            if (index === this.active) {
 | 
			
		||||
              classesTab.push('active')
 | 
			
		||||
              classesWrapper.push('active')
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
        return (
 | 
			
		||||
          <div class={ classesWrapper.join(' ')}>
 | 
			
		||||
            <button disabled={slot.data.attrs.disabled} onClick={this.activateTab(index)} class={ classesTab.join(' ') }>{slot.data.attrs.label}</button>
 | 
			
		||||
          </div>
 | 
			
		||||
        )
 | 
			
		||||
      })
 | 
			
		||||
            return (
 | 
			
		||||
              <div class={ classesWrapper.join(' ')}>
 | 
			
		||||
                <button disabled={slot.data.attrs.disabled} onClick={this.activateTab(index)} class={ classesTab.join(' ') }>{slot.data.attrs.label}</button>
 | 
			
		||||
              </div>
 | 
			
		||||
            )
 | 
			
		||||
          })
 | 
			
		||||
 | 
			
		||||
    const contents = this.$slots.default.map((slot, index) => {
 | 
			
		||||
      if (!slot.tag) return
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,10 +1,5 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <Timeline
 | 
			
		||||
    :title="tag"
 | 
			
		||||
    :timeline="timeline"
 | 
			
		||||
    :timeline-name="'tag'"
 | 
			
		||||
    :tag="tag"
 | 
			
		||||
  />
 | 
			
		||||
  <Timeline :title="tag" :timeline="timeline" :timeline-name="'tag'" :tag="tag" />
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src='./tag_timeline.js'></script>
 | 
			
		||||
<script src='./tag_timeline.js'></script>
 | 
			
		||||
| 
						 | 
				
			
			@ -2,10 +2,8 @@
 | 
			
		|||
  <div>
 | 
			
		||||
    <div class="panel panel-default">
 | 
			
		||||
      <div class="panel-body">
 | 
			
		||||
        <div
 | 
			
		||||
          class="tos-content"
 | 
			
		||||
          v-html="content"
 | 
			
		||||
        />
 | 
			
		||||
        <div v-html="content" class="tos-content">
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -137,7 +137,7 @@ const Timeline = {
 | 
			
		|||
        if (top < 15 &&
 | 
			
		||||
            !this.paused &&
 | 
			
		||||
            !(this.unfocused && this.$store.state.config.pauseOnUnfocused)
 | 
			
		||||
        ) {
 | 
			
		||||
           ) {
 | 
			
		||||
          this.showNewStatuses()
 | 
			
		||||
        } else {
 | 
			
		||||
          this.paused = true
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -2,66 +2,41 @@
 | 
			
		|||
  <div :class="classes.root">
 | 
			
		||||
    <div :class="classes.header">
 | 
			
		||||
      <div class="title">
 | 
			
		||||
        {{ title }}
 | 
			
		||||
        {{title}}
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="timelineError"
 | 
			
		||||
        class="loadmore-error alert error"
 | 
			
		||||
        @click.prevent
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('timeline.error_fetching') }}
 | 
			
		||||
      <div @click.prevent class="loadmore-error alert error" v-if="timelineError">
 | 
			
		||||
        {{$t('timeline.error_fetching')}}
 | 
			
		||||
      </div>
 | 
			
		||||
      <button
 | 
			
		||||
        v-if="timeline.newStatusCount > 0 && !timelineError"
 | 
			
		||||
        class="loadmore-button"
 | 
			
		||||
        @click.prevent="showNewStatuses"
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('timeline.show_new') }}{{ newStatusCountStr }}
 | 
			
		||||
      <button @click.prevent="showNewStatuses" class="loadmore-button" v-if="timeline.newStatusCount > 0 && !timelineError">
 | 
			
		||||
        {{$t('timeline.show_new')}}{{newStatusCountStr}}
 | 
			
		||||
      </button>
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="!timeline.newStatusCount > 0 && !timelineError"
 | 
			
		||||
        class="loadmore-text faint"
 | 
			
		||||
        @click.prevent
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('timeline.up_to_date') }}
 | 
			
		||||
      <div @click.prevent class="loadmore-text faint" v-if="!timeline.newStatusCount > 0 && !timelineError">
 | 
			
		||||
        {{$t('timeline.up_to_date')}}
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div :class="classes.body">
 | 
			
		||||
      <div class="timeline">
 | 
			
		||||
        <conversation
 | 
			
		||||
        <conversation 
 | 
			
		||||
          v-for="status in timeline.visibleStatuses"
 | 
			
		||||
          :key="status.id"
 | 
			
		||||
          class="status-fadein"
 | 
			
		||||
          :key="status.id"
 | 
			
		||||
          :statusoid="status"
 | 
			
		||||
          :collapsable="true"
 | 
			
		||||
        />
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div :class="classes.footer">
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="count===0"
 | 
			
		||||
        class="new-status-notification text-center panel-footer faint"
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('timeline.no_statuses') }}
 | 
			
		||||
      <div v-if="count===0" class="new-status-notification text-center panel-footer faint">
 | 
			
		||||
        {{$t('timeline.no_statuses')}}
 | 
			
		||||
      </div>
 | 
			
		||||
      <div
 | 
			
		||||
        v-else-if="bottomedOut"
 | 
			
		||||
        class="new-status-notification text-center panel-footer faint"
 | 
			
		||||
      >
 | 
			
		||||
        {{ $t('timeline.no_more_statuses') }}
 | 
			
		||||
      <div v-else-if="bottomedOut" class="new-status-notification text-center panel-footer faint">
 | 
			
		||||
        {{$t('timeline.no_more_statuses')}}
 | 
			
		||||
      </div>
 | 
			
		||||
      <a
 | 
			
		||||
        v-else-if="!timeline.loading"
 | 
			
		||||
        href="#"
 | 
			
		||||
        @click.prevent="fetchOlderStatuses()"
 | 
			
		||||
      >
 | 
			
		||||
        <div class="new-status-notification text-center panel-footer">{{ $t('timeline.load_older') }}</div>
 | 
			
		||||
      <a v-else-if="!timeline.loading" href="#" v-on:click.prevent='fetchOlderStatuses()'>
 | 
			
		||||
        <div class="new-status-notification text-center panel-footer">{{$t('timeline.load_older')}}</div>
 | 
			
		||||
      </a>
 | 
			
		||||
      <div
 | 
			
		||||
        v-else
 | 
			
		||||
        class="new-status-notification text-center panel-footer"
 | 
			
		||||
      >
 | 
			
		||||
        <i class="icon-spin3 animate-spin" />
 | 
			
		||||
      <div v-else class="new-status-notification text-center panel-footer">
 | 
			
		||||
        <i class="icon-spin3 animate-spin"/>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -3,7 +3,7 @@
 | 
			
		|||
    class="avatar"
 | 
			
		||||
    :class="{ 'avatar-compact': compact, 'better-shadow': betterShadow }"
 | 
			
		||||
    :src="imgSrc"
 | 
			
		||||
    :image-load-error="imageLoadError"
 | 
			
		||||
    :imageLoadError="imageLoadError"
 | 
			
		||||
  />
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -22,15 +22,15 @@ export default {
 | 
			
		|||
  computed: {
 | 
			
		||||
    classes () {
 | 
			
		||||
      return [{
 | 
			
		||||
        'user-card-rounded-t': this.rounded === 'top', // set border-top-left-radius and border-top-right-radius
 | 
			
		||||
        'user-card-rounded': this.rounded === true, // set border-radius for all sides
 | 
			
		||||
        'user-card-bordered': this.bordered === true // set border for all sides
 | 
			
		||||
        'user-card-rounded-t': this.rounded === 'top',  // set border-top-left-radius and border-top-right-radius
 | 
			
		||||
        'user-card-rounded': this.rounded === true,     // set border-radius for all sides
 | 
			
		||||
        'user-card-bordered': this.bordered === true    // set border for all sides
 | 
			
		||||
      }]
 | 
			
		||||
    },
 | 
			
		||||
    style () {
 | 
			
		||||
      const color = this.$store.state.config.customTheme.colors
 | 
			
		||||
        ? this.$store.state.config.customTheme.colors.bg // v2
 | 
			
		||||
        : this.$store.state.config.colors.bg // v1
 | 
			
		||||
            ? this.$store.state.config.customTheme.colors.bg  // v2
 | 
			
		||||
            : this.$store.state.config.colors.bg // v1
 | 
			
		||||
 | 
			
		||||
      if (color) {
 | 
			
		||||
        const rgb = (typeof color === 'string') ? hex2rgb(color) : color
 | 
			
		||||
| 
						 | 
				
			
			@ -72,12 +72,12 @@ export default {
 | 
			
		|||
    userHighlightType: {
 | 
			
		||||
      get () {
 | 
			
		||||
        const data = this.$store.state.config.highlight[this.user.screen_name]
 | 
			
		||||
        return (data && data.type) || 'disabled'
 | 
			
		||||
        return data && data.type || 'disabled'
 | 
			
		||||
      },
 | 
			
		||||
      set (type) {
 | 
			
		||||
        const data = this.$store.state.config.highlight[this.user.screen_name]
 | 
			
		||||
        if (type !== 'disabled') {
 | 
			
		||||
          this.$store.dispatch('setHighlight', { user: this.user.screen_name, color: (data && data.color) || '#FFFFFF', type })
 | 
			
		||||
          this.$store.dispatch('setHighlight', { user: this.user.screen_name, color: data && data.color || '#FFFFFF', type })
 | 
			
		||||
        } else {
 | 
			
		||||
          this.$store.dispatch('setHighlight', { user: this.user.screen_name, color: undefined })
 | 
			
		||||
        }
 | 
			
		||||
| 
						 | 
				
			
			@ -107,7 +107,7 @@ export default {
 | 
			
		|||
    followUser () {
 | 
			
		||||
      const store = this.$store
 | 
			
		||||
      this.followRequestInProgress = true
 | 
			
		||||
      requestFollow(this.user, store).then(({ sent }) => {
 | 
			
		||||
      requestFollow(this.user, store).then(({sent}) => {
 | 
			
		||||
        this.followRequestInProgress = false
 | 
			
		||||
        this.followRequestSent = sent
 | 
			
		||||
      })
 | 
			
		||||
| 
						 | 
				
			
			@ -138,7 +138,7 @@ export default {
 | 
			
		|||
        store.commit('setProfileView', { v })
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    linkClicked ({ target }) {
 | 
			
		||||
    linkClicked ({target}) {
 | 
			
		||||
      if (target.tagName === 'SPAN') {
 | 
			
		||||
        target = target.parentNode
 | 
			
		||||
      }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,240 +1,126 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div
 | 
			
		||||
    class="user-card"
 | 
			
		||||
    :class="classes"
 | 
			
		||||
    :style="style"
 | 
			
		||||
  >
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      <div class="user-info">
 | 
			
		||||
        <div class="container">
 | 
			
		||||
          <router-link :to="userProfileLink(user)">
 | 
			
		||||
            <UserAvatar
 | 
			
		||||
              :better-shadow="betterShadow"
 | 
			
		||||
              :src="user.profile_image_url_original"
 | 
			
		||||
            />
 | 
			
		||||
          </router-link>
 | 
			
		||||
          <div class="name-and-screen-name">
 | 
			
		||||
            <div class="top-line">
 | 
			
		||||
              <div
 | 
			
		||||
                v-if="user.name_html"
 | 
			
		||||
                :title="user.name"
 | 
			
		||||
                class="user-name"
 | 
			
		||||
                v-html="user.name_html"
 | 
			
		||||
              />
 | 
			
		||||
              <div
 | 
			
		||||
                v-else
 | 
			
		||||
                :title="user.name"
 | 
			
		||||
                class="user-name"
 | 
			
		||||
              >
 | 
			
		||||
                {{ user.name }}
 | 
			
		||||
              </div>
 | 
			
		||||
              <router-link
 | 
			
		||||
                v-if="!isOtherUser"
 | 
			
		||||
                :to="{ name: 'user-settings' }"
 | 
			
		||||
              >
 | 
			
		||||
                <i
 | 
			
		||||
                  class="button-icon icon-pencil usersettings"
 | 
			
		||||
                  :title="$t('tool_tip.user_settings')"
 | 
			
		||||
                />
 | 
			
		||||
              </router-link>
 | 
			
		||||
              <a
 | 
			
		||||
                v-if="isOtherUser && !user.is_local"
 | 
			
		||||
                :href="user.statusnet_profile_url"
 | 
			
		||||
                target="_blank"
 | 
			
		||||
              >
 | 
			
		||||
                <i class="icon-link-ext usersettings" />
 | 
			
		||||
              </a>
 | 
			
		||||
            </div>
 | 
			
		||||
 | 
			
		||||
            <router-link
 | 
			
		||||
              class="user-screen-name"
 | 
			
		||||
              :to="userProfileLink(user)"
 | 
			
		||||
            >
 | 
			
		||||
              <span class="handle">@{{ user.screen_name }}
 | 
			
		||||
                <span
 | 
			
		||||
                  v-if="!hideBio && !!visibleRole"
 | 
			
		||||
                  class="alert staff"
 | 
			
		||||
                >{{ visibleRole }}</span>
 | 
			
		||||
              </span><span v-if="user.locked"><i class="icon icon-lock" /></span>
 | 
			
		||||
              <span
 | 
			
		||||
                v-if="!hideUserStatsLocal && !hideBio"
 | 
			
		||||
                class="dailyAvg"
 | 
			
		||||
              >{{ dailyAvg }} {{ $t('user_card.per_day') }}</span>
 | 
			
		||||
<div class="user-card" :class="classes" :style="style">
 | 
			
		||||
  <div class="panel-heading">
 | 
			
		||||
    <div class='user-info'>
 | 
			
		||||
      <div class='container'>
 | 
			
		||||
        <router-link :to="userProfileLink(user)">
 | 
			
		||||
          <UserAvatar :betterShadow="betterShadow" :src="user.profile_image_url_original"/>
 | 
			
		||||
        </router-link>
 | 
			
		||||
        <div class="name-and-screen-name">
 | 
			
		||||
          <div class="top-line">
 | 
			
		||||
            <div :title="user.name" class='user-name' v-if="user.name_html" v-html="user.name_html"></div>
 | 
			
		||||
            <div :title="user.name" class='user-name' v-else>{{user.name}}</div>
 | 
			
		||||
            <router-link :to="{ name: 'user-settings' }" v-if="!isOtherUser">
 | 
			
		||||
              <i class="button-icon icon-pencil usersettings" :title="$t('tool_tip.user_settings')"></i>
 | 
			
		||||
            </router-link>
 | 
			
		||||
            <a :href="user.statusnet_profile_url" target="_blank" v-if="isOtherUser && !user.is_local">
 | 
			
		||||
              <i class="icon-link-ext usersettings"></i>
 | 
			
		||||
            </a>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class="user-meta">
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="user.follows_you && loggedIn && isOtherUser"
 | 
			
		||||
            class="following"
 | 
			
		||||
          >
 | 
			
		||||
            {{ $t('user_card.follows_you') }}
 | 
			
		||||
          </div>
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="isOtherUser && (loggedIn || !switcher)"
 | 
			
		||||
            class="highlighter"
 | 
			
		||||
          >
 | 
			
		||||
            <!-- id's need to be unique, otherwise vue confuses which user-card checkbox belongs to -->
 | 
			
		||||
            <input
 | 
			
		||||
              v-if="userHighlightType !== 'disabled'"
 | 
			
		||||
              :id="'userHighlightColorTx'+user.id"
 | 
			
		||||
              v-model="userHighlightColor"
 | 
			
		||||
              class="userHighlightText"
 | 
			
		||||
              type="text"
 | 
			
		||||
            >
 | 
			
		||||
            <input
 | 
			
		||||
              v-if="userHighlightType !== 'disabled'"
 | 
			
		||||
              :id="'userHighlightColor'+user.id"
 | 
			
		||||
              v-model="userHighlightColor"
 | 
			
		||||
              class="userHighlightCl"
 | 
			
		||||
              type="color"
 | 
			
		||||
            >
 | 
			
		||||
            <label
 | 
			
		||||
              for="style-switcher"
 | 
			
		||||
              class="userHighlightSel select"
 | 
			
		||||
            >
 | 
			
		||||
              <select
 | 
			
		||||
                :id="'userHighlightSel'+user.id"
 | 
			
		||||
                v-model="userHighlightType"
 | 
			
		||||
                class="userHighlightSel"
 | 
			
		||||
              >
 | 
			
		||||
                <option value="disabled">No highlight</option>
 | 
			
		||||
                <option value="solid">Solid bg</option>
 | 
			
		||||
                <option value="striped">Striped bg</option>
 | 
			
		||||
                <option value="side">Side stripe</option>
 | 
			
		||||
              </select>
 | 
			
		||||
              <i class="icon-down-open" />
 | 
			
		||||
            </label>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="isOtherUser"
 | 
			
		||||
          class="user-interactions"
 | 
			
		||||
        >
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="loggedIn"
 | 
			
		||||
            class="follow"
 | 
			
		||||
          >
 | 
			
		||||
            <span v-if="user.following">
 | 
			
		||||
              <!--Following them!-->
 | 
			
		||||
              <button
 | 
			
		||||
                class="pressed"
 | 
			
		||||
                :disabled="followRequestInProgress"
 | 
			
		||||
                :title="$t('user_card.follow_unfollow')"
 | 
			
		||||
                @click="unfollowUser"
 | 
			
		||||
              >
 | 
			
		||||
                <template v-if="followRequestInProgress">
 | 
			
		||||
                  {{ $t('user_card.follow_progress') }}
 | 
			
		||||
                </template>
 | 
			
		||||
                <template v-else>
 | 
			
		||||
                  {{ $t('user_card.following') }}
 | 
			
		||||
                </template>
 | 
			
		||||
              </button>
 | 
			
		||||
            </span>
 | 
			
		||||
            <span v-if="!user.following">
 | 
			
		||||
              <button
 | 
			
		||||
                :disabled="followRequestInProgress"
 | 
			
		||||
                :title="followRequestSent ? $t('user_card.follow_again') : ''"
 | 
			
		||||
                @click="followUser"
 | 
			
		||||
              >
 | 
			
		||||
                <template v-if="followRequestInProgress">
 | 
			
		||||
                  {{ $t('user_card.follow_progress') }}
 | 
			
		||||
                </template>
 | 
			
		||||
                <template v-else-if="followRequestSent">
 | 
			
		||||
                  {{ $t('user_card.follow_sent') }}
 | 
			
		||||
                </template>
 | 
			
		||||
                <template v-else>
 | 
			
		||||
                  {{ $t('user_card.follow') }}
 | 
			
		||||
                </template>
 | 
			
		||||
              </button>
 | 
			
		||||
            </span>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="isOtherUser && loggedIn"
 | 
			
		||||
            class="mute"
 | 
			
		||||
          >
 | 
			
		||||
            <span v-if="user.muted">
 | 
			
		||||
              <button
 | 
			
		||||
                class="pressed"
 | 
			
		||||
                @click="unmuteUser"
 | 
			
		||||
              >
 | 
			
		||||
                {{ $t('user_card.muted') }}
 | 
			
		||||
              </button>
 | 
			
		||||
            </span>
 | 
			
		||||
            <span v-if="!user.muted">
 | 
			
		||||
              <button @click="muteUser">
 | 
			
		||||
                {{ $t('user_card.mute') }}
 | 
			
		||||
              </button>
 | 
			
		||||
            </span>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div v-if="!loggedIn && user.is_local">
 | 
			
		||||
            <RemoteFollow :user="user" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="isOtherUser && loggedIn"
 | 
			
		||||
            class="block"
 | 
			
		||||
          >
 | 
			
		||||
            <span v-if="user.statusnet_blocking">
 | 
			
		||||
              <button
 | 
			
		||||
                class="pressed"
 | 
			
		||||
                @click="unblockUser"
 | 
			
		||||
              >
 | 
			
		||||
                {{ $t('user_card.blocked') }}
 | 
			
		||||
              </button>
 | 
			
		||||
            </span>
 | 
			
		||||
            <span v-if="!user.statusnet_blocking">
 | 
			
		||||
              <button @click="blockUser">
 | 
			
		||||
                {{ $t('user_card.block') }}
 | 
			
		||||
              </button>
 | 
			
		||||
            </span>
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <router-link class='user-screen-name' :to="userProfileLink(user)">
 | 
			
		||||
            <span class="handle">@{{user.screen_name}}
 | 
			
		||||
              <span class="alert staff" v-if="!hideBio && !!visibleRole">{{visibleRole}}</span>
 | 
			
		||||
            </span><span v-if="user.locked"><i class="icon icon-lock"></i></span>
 | 
			
		||||
            <span v-if="!hideUserStatsLocal && !hideBio" class="dailyAvg">{{dailyAvg}} {{ $t('user_card.per_day') }}</span>
 | 
			
		||||
          </router-link>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="!hideBio"
 | 
			
		||||
      class="panel-body"
 | 
			
		||||
    >
 | 
			
		||||
      <div
 | 
			
		||||
        v-if="!hideUserStatsLocal && switcher"
 | 
			
		||||
        class="user-counts"
 | 
			
		||||
      >
 | 
			
		||||
        <div
 | 
			
		||||
          class="user-count"
 | 
			
		||||
          @click.prevent="setProfileView('statuses')"
 | 
			
		||||
        >
 | 
			
		||||
          <h5>{{ $t('user_card.statuses') }}</h5>
 | 
			
		||||
          <span>{{ user.statuses_count }} <br></span>
 | 
			
		||||
      <div class="user-meta">
 | 
			
		||||
        <div v-if="user.follows_you && loggedIn && isOtherUser" class="following">
 | 
			
		||||
          {{ $t('user_card.follows_you') }}
 | 
			
		||||
        </div>
 | 
			
		||||
        <div
 | 
			
		||||
          class="user-count"
 | 
			
		||||
          @click.prevent="setProfileView('friends')"
 | 
			
		||||
        >
 | 
			
		||||
          <h5>{{ $t('user_card.followees') }}</h5>
 | 
			
		||||
          <span>{{ user.friends_count }}</span>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div
 | 
			
		||||
          class="user-count"
 | 
			
		||||
          @click.prevent="setProfileView('followers')"
 | 
			
		||||
        >
 | 
			
		||||
          <h5>{{ $t('user_card.followers') }}</h5>
 | 
			
		||||
          <span>{{ user.followers_count }}</span>
 | 
			
		||||
        <div class="highlighter" v-if="isOtherUser && (loggedIn || !switcher)">
 | 
			
		||||
          <!-- id's need to be unique, otherwise vue confuses which user-card checkbox belongs to -->
 | 
			
		||||
          <input class="userHighlightText" type="text" :id="'userHighlightColorTx'+user.id" v-if="userHighlightType !== 'disabled'" v-model="userHighlightColor"/>
 | 
			
		||||
          <input class="userHighlightCl" type="color" :id="'userHighlightColor'+user.id" v-if="userHighlightType !== 'disabled'" v-model="userHighlightColor"/>
 | 
			
		||||
          <label for="style-switcher" class='userHighlightSel select'>
 | 
			
		||||
            <select class="userHighlightSel" :id="'userHighlightSel'+user.id" v-model="userHighlightType">
 | 
			
		||||
              <option value="disabled">No highlight</option>
 | 
			
		||||
              <option value="solid">Solid bg</option>
 | 
			
		||||
              <option value="striped">Striped bg</option>
 | 
			
		||||
              <option value="side">Side stripe</option>
 | 
			
		||||
            </select>
 | 
			
		||||
            <i class="icon-down-open"/>
 | 
			
		||||
          </label>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div v-if="isOtherUser" class="user-interactions">
 | 
			
		||||
        <div class="follow" v-if="loggedIn">
 | 
			
		||||
          <span v-if="user.following">
 | 
			
		||||
            <!--Following them!-->
 | 
			
		||||
            <button @click="unfollowUser" class="pressed" :disabled="followRequestInProgress" :title="$t('user_card.follow_unfollow')">
 | 
			
		||||
              <template v-if="followRequestInProgress">
 | 
			
		||||
                {{ $t('user_card.follow_progress') }}
 | 
			
		||||
              </template>
 | 
			
		||||
              <template v-else>
 | 
			
		||||
                {{ $t('user_card.following') }}
 | 
			
		||||
              </template>
 | 
			
		||||
            </button>
 | 
			
		||||
          </span>
 | 
			
		||||
          <span v-if="!user.following">
 | 
			
		||||
            <button @click="followUser" :disabled="followRequestInProgress" :title="followRequestSent ? $t('user_card.follow_again') : ''">
 | 
			
		||||
              <template v-if="followRequestInProgress">
 | 
			
		||||
                {{ $t('user_card.follow_progress') }}
 | 
			
		||||
              </template>
 | 
			
		||||
              <template v-else-if="followRequestSent">
 | 
			
		||||
                {{ $t('user_card.follow_sent') }}
 | 
			
		||||
              </template>
 | 
			
		||||
              <template v-else>
 | 
			
		||||
                {{ $t('user_card.follow') }}
 | 
			
		||||
              </template>
 | 
			
		||||
            </button>
 | 
			
		||||
          </span>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class='mute' v-if='isOtherUser && loggedIn'>
 | 
			
		||||
          <span v-if='user.muted'>
 | 
			
		||||
            <button @click="unmuteUser" class="pressed">
 | 
			
		||||
              {{ $t('user_card.muted') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </span>
 | 
			
		||||
          <span v-if='!user.muted'>
 | 
			
		||||
            <button @click="muteUser">
 | 
			
		||||
              {{ $t('user_card.mute') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </span>
 | 
			
		||||
        </div>
 | 
			
		||||
        <div v-if='!loggedIn && user.is_local'>
 | 
			
		||||
          <RemoteFollow :user="user" />
 | 
			
		||||
        </div>
 | 
			
		||||
        <div class='block' v-if='isOtherUser && loggedIn'>
 | 
			
		||||
          <span v-if='user.statusnet_blocking'>
 | 
			
		||||
            <button @click="unblockUser" class="pressed">
 | 
			
		||||
              {{ $t('user_card.blocked') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </span>
 | 
			
		||||
          <span v-if='!user.statusnet_blocking'>
 | 
			
		||||
            <button @click="blockUser">
 | 
			
		||||
              {{ $t('user_card.block') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          </span>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <p
 | 
			
		||||
        v-if="!hideBio && user.description_html"
 | 
			
		||||
        class="user-card-bio"
 | 
			
		||||
        @click.prevent="linkClicked"
 | 
			
		||||
        v-html="user.description_html"
 | 
			
		||||
      />
 | 
			
		||||
      <p
 | 
			
		||||
        v-else-if="!hideBio"
 | 
			
		||||
        class="user-card-bio"
 | 
			
		||||
      >
 | 
			
		||||
        {{ user.description }}
 | 
			
		||||
      </p>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
  <div class="panel-body" v-if="!hideBio">
 | 
			
		||||
    <div v-if="!hideUserStatsLocal && switcher" class="user-counts">
 | 
			
		||||
      <div class="user-count" v-on:click.prevent="setProfileView('statuses')">
 | 
			
		||||
        <h5>{{ $t('user_card.statuses') }}</h5>
 | 
			
		||||
        <span>{{user.statuses_count}} <br></span>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="user-count" v-on:click.prevent="setProfileView('friends')">
 | 
			
		||||
        <h5>{{ $t('user_card.followees') }}</h5>
 | 
			
		||||
        <span>{{user.friends_count}}</span>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="user-count" v-on:click.prevent="setProfileView('followers')">
 | 
			
		||||
        <h5>{{ $t('user_card.followers') }}</h5>
 | 
			
		||||
        <span>{{user.followers_count}}</span>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <p @click.prevent="linkClicked" v-if="!hideBio && user.description_html" class="user-card-bio" v-html="user.description_html"></p>
 | 
			
		||||
    <p v-else-if="!hideBio" class="user-card-bio">{{ user.description }}</p>
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./user_card.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,38 +1,14 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div>
 | 
			
		||||
    <div class="user-finder-container">
 | 
			
		||||
      <i
 | 
			
		||||
        v-if="loading"
 | 
			
		||||
        class="icon-spin4 user-finder-icon animate-spin-slow"
 | 
			
		||||
      />
 | 
			
		||||
      <a
 | 
			
		||||
        v-if="hidden"
 | 
			
		||||
        href="#"
 | 
			
		||||
        :title="$t('finder.find_user')"
 | 
			
		||||
      ><i
 | 
			
		||||
        class="icon-user-plus user-finder-icon"
 | 
			
		||||
        @click.prevent.stop="toggleHidden"
 | 
			
		||||
      /></a>
 | 
			
		||||
      <i class="icon-spin4 user-finder-icon animate-spin-slow" v-if="loading" />
 | 
			
		||||
      <a href="#" v-if="hidden" :title="$t('finder.find_user')"><i class="icon-user-plus user-finder-icon" @click.prevent.stop="toggleHidden" /></a>
 | 
			
		||||
      <template v-else>
 | 
			
		||||
        <input
 | 
			
		||||
          id="user-finder-input"
 | 
			
		||||
          ref="userSearchInput"
 | 
			
		||||
          v-model="username"
 | 
			
		||||
          class="user-finder-input"
 | 
			
		||||
          :placeholder="$t('finder.find_user')"
 | 
			
		||||
          type="text"
 | 
			
		||||
          @keyup.enter="findUser(username)"
 | 
			
		||||
        >
 | 
			
		||||
        <button
 | 
			
		||||
          class="btn search-button"
 | 
			
		||||
          @click="findUser(username)"
 | 
			
		||||
        >
 | 
			
		||||
          <i class="icon-search" />
 | 
			
		||||
        <input class="user-finder-input" ref="userSearchInput" @keyup.enter="findUser(username)" v-model="username" :placeholder="$t('finder.find_user')" id="user-finder-input" type="text"/>
 | 
			
		||||
        <button class="btn search-button" @click="findUser(username)">
 | 
			
		||||
          <i class="icon-search"/>
 | 
			
		||||
        </button>
 | 
			
		||||
        <i
 | 
			
		||||
          class="button-icon icon-cancel user-finder-icon"
 | 
			
		||||
          @click.prevent.stop="toggleHidden"
 | 
			
		||||
        />
 | 
			
		||||
        <i class="button-icon icon-cancel user-finder-icon" @click.prevent.stop="toggleHidden"/>
 | 
			
		||||
      </template>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			@ -49,6 +25,7 @@
 | 
			
		|||
  align-items: baseline;
 | 
			
		||||
  vertical-align: baseline;
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
  .user-finder-input,
 | 
			
		||||
  .search-button {
 | 
			
		||||
    height: 29px;
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,20 +1,12 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="user-panel">
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="user"
 | 
			
		||||
      class="panel panel-default"
 | 
			
		||||
      style="overflow: visible;"
 | 
			
		||||
    >
 | 
			
		||||
      <UserCard
 | 
			
		||||
        :user="user"
 | 
			
		||||
        :hide-bio="true"
 | 
			
		||||
        rounded="top"
 | 
			
		||||
      />
 | 
			
		||||
    <div v-if='user' class="panel panel-default" style="overflow: visible;">
 | 
			
		||||
      <UserCard :user="user" :hideBio="true" rounded="top"/>
 | 
			
		||||
      <div class="panel-footer">
 | 
			
		||||
        <post-status-form v-if="user" />
 | 
			
		||||
        <post-status-form v-if='user'></post-status-form>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <login-form v-if="!user" />
 | 
			
		||||
    <login-form v-if='!user'></login-form>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,84 +1,55 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div>
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="user.id"
 | 
			
		||||
      class="user-profile panel panel-default"
 | 
			
		||||
    >
 | 
			
		||||
      <UserCard
 | 
			
		||||
        :user="user"
 | 
			
		||||
        :switcher="true"
 | 
			
		||||
        :selected="timeline.viewing"
 | 
			
		||||
        rounded="top"
 | 
			
		||||
<div>
 | 
			
		||||
  <div v-if="user.id" class="user-profile panel panel-default">
 | 
			
		||||
    <UserCard :user="user" :switcher="true" :selected="timeline.viewing" rounded="top"/>
 | 
			
		||||
    <tab-switcher :renderOnlyFocused="true" ref="tabSwitcher">
 | 
			
		||||
      <Timeline
 | 
			
		||||
        :label="$t('user_card.statuses')"
 | 
			
		||||
        :disabled="!user.statuses_count"
 | 
			
		||||
        :count="user.statuses_count"
 | 
			
		||||
        :embedded="true"
 | 
			
		||||
        :title="$t('user_profile.timeline_title')"
 | 
			
		||||
        :timeline="timeline"
 | 
			
		||||
        :timeline-name="'user'"
 | 
			
		||||
        :user-id="userId"
 | 
			
		||||
      />
 | 
			
		||||
      <tab-switcher
 | 
			
		||||
        ref="tabSwitcher"
 | 
			
		||||
        :render-only-focused="true"
 | 
			
		||||
      >
 | 
			
		||||
        <Timeline
 | 
			
		||||
          :label="$t('user_card.statuses')"
 | 
			
		||||
          :disabled="!user.statuses_count"
 | 
			
		||||
          :count="user.statuses_count"
 | 
			
		||||
          :embedded="true"
 | 
			
		||||
          :title="$t('user_profile.timeline_title')"
 | 
			
		||||
          :timeline="timeline"
 | 
			
		||||
          :timeline-name="'user'"
 | 
			
		||||
          :user-id="userId"
 | 
			
		||||
        />
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="followsTabVisible"
 | 
			
		||||
          :label="$t('user_card.followees')"
 | 
			
		||||
          :disabled="!user.friends_count"
 | 
			
		||||
        >
 | 
			
		||||
          <FriendList :user-id="userId" />
 | 
			
		||||
        </div>
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="followersTabVisible"
 | 
			
		||||
          :label="$t('user_card.followers')"
 | 
			
		||||
          :disabled="!user.followers_count"
 | 
			
		||||
        >
 | 
			
		||||
          <FollowerList
 | 
			
		||||
            :user-id="userId"
 | 
			
		||||
            :entry-props="{noFollowsYou: isUs}"
 | 
			
		||||
          />
 | 
			
		||||
        </div>
 | 
			
		||||
        <Timeline
 | 
			
		||||
          :label="$t('user_card.media')"
 | 
			
		||||
          :disabled="!media.visibleStatuses.length"
 | 
			
		||||
          :embedded="true"
 | 
			
		||||
          :title="$t('user_card.media')"
 | 
			
		||||
          timeline-name="media"
 | 
			
		||||
          :timeline="media"
 | 
			
		||||
          :user-id="userId"
 | 
			
		||||
        />
 | 
			
		||||
        <Timeline
 | 
			
		||||
          v-if="isUs"
 | 
			
		||||
          :label="$t('user_card.favorites')"
 | 
			
		||||
          :disabled="!favorites.visibleStatuses.length"
 | 
			
		||||
          :embedded="true"
 | 
			
		||||
          :title="$t('user_card.favorites')"
 | 
			
		||||
          timeline-name="favorites"
 | 
			
		||||
          :timeline="favorites"
 | 
			
		||||
        />
 | 
			
		||||
      </tab-switcher>
 | 
			
		||||
      <div :label="$t('user_card.followees')" v-if="followsTabVisible" :disabled="!user.friends_count">
 | 
			
		||||
        <FriendList :userId="userId" />
 | 
			
		||||
      </div>
 | 
			
		||||
      <div :label="$t('user_card.followers')" v-if="followersTabVisible" :disabled="!user.followers_count">
 | 
			
		||||
        <FollowerList :userId="userId" :entryProps="{noFollowsYou: isUs}" />
 | 
			
		||||
      </div>
 | 
			
		||||
      <Timeline
 | 
			
		||||
        :label="$t('user_card.media')"
 | 
			
		||||
        :disabled="!media.visibleStatuses.length"
 | 
			
		||||
        :embedded="true" :title="$t('user_card.media')"
 | 
			
		||||
        timeline-name="media"
 | 
			
		||||
        :timeline="media"
 | 
			
		||||
        :user-id="userId"
 | 
			
		||||
      />
 | 
			
		||||
      <Timeline
 | 
			
		||||
        v-if="isUs"
 | 
			
		||||
        :label="$t('user_card.favorites')"
 | 
			
		||||
        :disabled="!favorites.visibleStatuses.length"
 | 
			
		||||
        :embedded="true"
 | 
			
		||||
        :title="$t('user_card.favorites')"
 | 
			
		||||
        timeline-name="favorites"
 | 
			
		||||
        :timeline="favorites"
 | 
			
		||||
      />
 | 
			
		||||
    </tab-switcher>
 | 
			
		||||
  </div>
 | 
			
		||||
  <div v-else class="panel user-profile-placeholder">
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      <div class="title">
 | 
			
		||||
        {{ $t('settings.profile_tab') }}
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div
 | 
			
		||||
      v-else
 | 
			
		||||
      class="panel user-profile-placeholder"
 | 
			
		||||
    >
 | 
			
		||||
      <div class="panel-heading">
 | 
			
		||||
        <div class="title">
 | 
			
		||||
          {{ $t('settings.profile_tab') }}
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="panel-body">
 | 
			
		||||
        <span v-if="error">{{ error }}</span>
 | 
			
		||||
        <i
 | 
			
		||||
          v-else
 | 
			
		||||
          class="icon-spin3 animate-spin"
 | 
			
		||||
        />
 | 
			
		||||
      </div>
 | 
			
		||||
    <div class="panel-body">
 | 
			
		||||
      <span v-if="error">{{ error }}</span>
 | 
			
		||||
      <i class="icon-spin3 animate-spin" v-else></i>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
</div>
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
<script src="./user_profile.js"></script>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -33,7 +33,7 @@ const userSearch = {
 | 
			
		|||
        return
 | 
			
		||||
      }
 | 
			
		||||
      this.loading = true
 | 
			
		||||
      userSearchApi.search({ query, store: this.$store })
 | 
			
		||||
      userSearchApi.search({query, store: this.$store})
 | 
			
		||||
        .then((res) => {
 | 
			
		||||
          this.loading = false
 | 
			
		||||
          this.users = res
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,38 +1,19 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="user-search panel panel-default">
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      {{ $t('nav.user_search') }}
 | 
			
		||||
      {{$t('nav.user_search')}}
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="user-search-input-container">
 | 
			
		||||
      <input
 | 
			
		||||
        ref="userSearchInput"
 | 
			
		||||
        v-model="username"
 | 
			
		||||
        class="user-finder-input"
 | 
			
		||||
        :placeholder="$t('finder.find_user')"
 | 
			
		||||
        @keyup.enter="newQuery(username)"
 | 
			
		||||
      >
 | 
			
		||||
      <button
 | 
			
		||||
        class="btn search-button"
 | 
			
		||||
        @click="newQuery(username)"
 | 
			
		||||
      >
 | 
			
		||||
        <i class="icon-search" />
 | 
			
		||||
      <input class="user-finder-input" ref="userSearchInput" @keyup.enter="newQuery(username)" v-model="username" :placeholder="$t('finder.find_user')"/>
 | 
			
		||||
      <button class="btn search-button" @click="newQuery(username)">
 | 
			
		||||
        <i class="icon-search"/>
 | 
			
		||||
      </button>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div
 | 
			
		||||
      v-if="loading"
 | 
			
		||||
      class="text-center loading-icon"
 | 
			
		||||
    >
 | 
			
		||||
      <i class="icon-spin3 animate-spin" />
 | 
			
		||||
    <div v-if="loading" class="text-center loading-icon">
 | 
			
		||||
      <i class="icon-spin3 animate-spin"/>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div
 | 
			
		||||
      v-else
 | 
			
		||||
      class="panel-body"
 | 
			
		||||
    >
 | 
			
		||||
      <FollowCard
 | 
			
		||||
        v-for="user in users"
 | 
			
		||||
        :key="user.id"
 | 
			
		||||
        :user="user"
 | 
			
		||||
      />
 | 
			
		||||
    <div v-else class="panel-body">
 | 
			
		||||
      <FollowCard v-for="user in users" :key="user.id" :user="user"/>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -134,12 +134,12 @@ const UserSettings = {
 | 
			
		|||
            hide_followers,
 | 
			
		||||
            show_role
 | 
			
		||||
            /* eslint-enable camelcase */
 | 
			
		||||
          } }).then((user) => {
 | 
			
		||||
          if (!user.error) {
 | 
			
		||||
            this.$store.commit('addNewUsers', [user])
 | 
			
		||||
            this.$store.commit('setCurrentUser', user)
 | 
			
		||||
          }
 | 
			
		||||
        })
 | 
			
		||||
          }}).then((user) => {
 | 
			
		||||
            if (!user.error) {
 | 
			
		||||
              this.$store.commit('addNewUsers', [user])
 | 
			
		||||
              this.$store.commit('setCurrentUser', user)
 | 
			
		||||
            }
 | 
			
		||||
          })
 | 
			
		||||
    },
 | 
			
		||||
    changeVis (visibility) {
 | 
			
		||||
      this.newDefaultScope = visibility
 | 
			
		||||
| 
						 | 
				
			
			@ -150,12 +150,12 @@ const UserSettings = {
 | 
			
		|||
      if (file.size > this.$store.state.instance[slot + 'limit']) {
 | 
			
		||||
        const filesize = fileSizeFormatService.fileSizeFormat(file.size)
 | 
			
		||||
        const allowedsize = fileSizeFormatService.fileSizeFormat(this.$store.state.instance[slot + 'limit'])
 | 
			
		||||
        this[slot + 'UploadError'] = this.$t('upload.error.base') + ' ' + this.$t('upload.error.file_too_big', { filesize: filesize.num, filesizeunit: filesize.unit, allowedsize: allowedsize.num, allowedsizeunit: allowedsize.unit })
 | 
			
		||||
        this[slot + 'UploadError'] = this.$t('upload.error.base') + ' ' + this.$t('upload.error.file_too_big', {filesize: filesize.num, filesizeunit: filesize.unit, allowedsize: allowedsize.num, allowedsizeunit: allowedsize.unit})
 | 
			
		||||
        return
 | 
			
		||||
      }
 | 
			
		||||
      // eslint-disable-next-line no-undef
 | 
			
		||||
      const reader = new FileReader()
 | 
			
		||||
      reader.onload = ({ target }) => {
 | 
			
		||||
      reader.onload = ({target}) => {
 | 
			
		||||
        const img = target.result
 | 
			
		||||
        this[slot + 'Preview'] = img
 | 
			
		||||
      }
 | 
			
		||||
| 
						 | 
				
			
			@ -195,7 +195,7 @@ const UserSettings = {
 | 
			
		|||
      offset_top = 0
 | 
			
		||||
      offset_left = 0
 | 
			
		||||
      this.bannerUploading = true
 | 
			
		||||
      this.$store.state.api.backendInteractor.updateBanner({ params: { banner, offset_top, offset_left, width, height } }).then((data) => {
 | 
			
		||||
      this.$store.state.api.backendInteractor.updateBanner({params: {banner, offset_top, offset_left, width, height}}).then((data) => {
 | 
			
		||||
        if (!data.error) {
 | 
			
		||||
          let clone = JSON.parse(JSON.stringify(this.$store.state.users.currentUser))
 | 
			
		||||
          clone.cover_photo = data.url
 | 
			
		||||
| 
						 | 
				
			
			@ -221,7 +221,7 @@ const UserSettings = {
 | 
			
		|||
      cropW = imginfo.width
 | 
			
		||||
      cropH = imginfo.width
 | 
			
		||||
      this.backgroundUploading = true
 | 
			
		||||
      this.$store.state.api.backendInteractor.updateBg({ params: { img, cropX, cropY, cropW, cropH } }).then((data) => {
 | 
			
		||||
      this.$store.state.api.backendInteractor.updateBg({params: {img, cropX, cropY, cropW, cropH}}).then((data) => {
 | 
			
		||||
        if (!data.error) {
 | 
			
		||||
          let clone = JSON.parse(JSON.stringify(this.$store.state.users.currentUser))
 | 
			
		||||
          clone.background_image = data.url
 | 
			
		||||
| 
						 | 
				
			
			@ -237,7 +237,7 @@ const UserSettings = {
 | 
			
		|||
    importFollows () {
 | 
			
		||||
      this.followListUploading = true
 | 
			
		||||
      const followList = this.followList
 | 
			
		||||
      this.$store.state.api.backendInteractor.followImport({ params: followList })
 | 
			
		||||
      this.$store.state.api.backendInteractor.followImport({params: followList})
 | 
			
		||||
        .then((status) => {
 | 
			
		||||
          if (status) {
 | 
			
		||||
            this.followsImported = true
 | 
			
		||||
| 
						 | 
				
			
			@ -295,11 +295,11 @@ const UserSettings = {
 | 
			
		|||
      this.deletingAccount = true
 | 
			
		||||
    },
 | 
			
		||||
    deleteAccount () {
 | 
			
		||||
      this.$store.state.api.backendInteractor.deleteAccount({ password: this.deleteAccountConfirmPasswordInput })
 | 
			
		||||
      this.$store.state.api.backendInteractor.deleteAccount({password: this.deleteAccountConfirmPasswordInput})
 | 
			
		||||
        .then((res) => {
 | 
			
		||||
          if (res.status === 'success') {
 | 
			
		||||
            this.$store.dispatch('logout')
 | 
			
		||||
            this.$router.push({ name: 'root' })
 | 
			
		||||
            this.$router.push({name: 'root'})
 | 
			
		||||
          } else {
 | 
			
		||||
            this.deleteAccountError = res.error
 | 
			
		||||
          }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -2,23 +2,15 @@
 | 
			
		|||
  <div class="settings panel panel-default">
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      <div class="title">
 | 
			
		||||
        {{ $t('settings.user_settings') }}
 | 
			
		||||
        {{$t('settings.user_settings')}}
 | 
			
		||||
      </div>
 | 
			
		||||
      <transition name="fade">
 | 
			
		||||
        <template v-if="currentSaveStateNotice">
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="currentSaveStateNotice.error"
 | 
			
		||||
            class="alert error"
 | 
			
		||||
            @click.prevent
 | 
			
		||||
          >
 | 
			
		||||
          <div @click.prevent class="alert error" v-if="currentSaveStateNotice.error">
 | 
			
		||||
            {{ $t('settings.saving_err') }}
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="!currentSaveStateNotice.error"
 | 
			
		||||
            class="alert transparent"
 | 
			
		||||
            @click.prevent
 | 
			
		||||
          >
 | 
			
		||||
          <div @click.prevent class="alert transparent" v-if="!currentSaveStateNotice.error">
 | 
			
		||||
            {{ $t('settings.saving_ok') }}
 | 
			
		||||
          </div>
 | 
			
		||||
        </template>
 | 
			
		||||
| 
						 | 
				
			
			@ -27,258 +19,132 @@
 | 
			
		|||
    <div class="panel-body profile-edit">
 | 
			
		||||
      <tab-switcher>
 | 
			
		||||
        <div :label="$t('settings.profile_tab')">
 | 
			
		||||
          <div class="setting-item">
 | 
			
		||||
            <h2>{{ $t('settings.name_bio') }}</h2>
 | 
			
		||||
            <p>{{ $t('settings.name') }}</p>
 | 
			
		||||
            <EmojiInput
 | 
			
		||||
              id="username"
 | 
			
		||||
              v-model="newName"
 | 
			
		||||
          <div class="setting-item" >
 | 
			
		||||
            <h2>{{$t('settings.name_bio')}}</h2>
 | 
			
		||||
            <p>{{$t('settings.name')}}</p>
 | 
			
		||||
            <EmojiInput 
 | 
			
		||||
              type="text"
 | 
			
		||||
              v-model="newName"
 | 
			
		||||
              id="username"
 | 
			
		||||
              classname="name-changer"
 | 
			
		||||
            />
 | 
			
		||||
            <p>{{ $t('settings.bio') }}</p>
 | 
			
		||||
            <p>{{$t('settings.bio')}}</p>
 | 
			
		||||
            <EmojiInput
 | 
			
		||||
              v-model="newBio"
 | 
			
		||||
              type="textarea"
 | 
			
		||||
              v-model="newBio"
 | 
			
		||||
              classname="bio"
 | 
			
		||||
            />
 | 
			
		||||
            <p>
 | 
			
		||||
              <input
 | 
			
		||||
                id="account-locked"
 | 
			
		||||
                v-model="newLocked"
 | 
			
		||||
                type="checkbox"
 | 
			
		||||
              >
 | 
			
		||||
              <label for="account-locked">{{ $t('settings.lock_account_description') }}</label>
 | 
			
		||||
              <input type="checkbox" v-model="newLocked" id="account-locked">
 | 
			
		||||
              <label for="account-locked">{{$t('settings.lock_account_description')}}</label>
 | 
			
		||||
            </p>
 | 
			
		||||
            <div>
 | 
			
		||||
              <label for="default-vis">{{ $t('settings.default_vis') }}</label>
 | 
			
		||||
              <div
 | 
			
		||||
                id="default-vis"
 | 
			
		||||
                class="visibility-tray"
 | 
			
		||||
              >
 | 
			
		||||
              <label for="default-vis">{{$t('settings.default_vis')}}</label>
 | 
			
		||||
              <div id="default-vis" class="visibility-tray">
 | 
			
		||||
                <scope-selector
 | 
			
		||||
                  :show-all="true"
 | 
			
		||||
                  :user-default="newDefaultScope"
 | 
			
		||||
                  :on-scope-change="changeVis"
 | 
			
		||||
                />
 | 
			
		||||
                  :showAll="true"
 | 
			
		||||
                  :userDefault="newDefaultScope"
 | 
			
		||||
                  :onScopeChange="changeVis"/>
 | 
			
		||||
              </div>
 | 
			
		||||
            </div>
 | 
			
		||||
            <p>
 | 
			
		||||
              <input
 | 
			
		||||
                id="account-no-rich-text"
 | 
			
		||||
                v-model="newNoRichText"
 | 
			
		||||
                type="checkbox"
 | 
			
		||||
              >
 | 
			
		||||
              <label for="account-no-rich-text">{{ $t('settings.no_rich_text_description') }}</label>
 | 
			
		||||
              <input type="checkbox" v-model="newNoRichText" id="account-no-rich-text">
 | 
			
		||||
              <label for="account-no-rich-text">{{$t('settings.no_rich_text_description')}}</label>
 | 
			
		||||
            </p>
 | 
			
		||||
            <p>
 | 
			
		||||
              <input
 | 
			
		||||
                id="account-hide-follows"
 | 
			
		||||
                v-model="hideFollows"
 | 
			
		||||
                type="checkbox"
 | 
			
		||||
              >
 | 
			
		||||
              <label for="account-hide-follows">{{ $t('settings.hide_follows_description') }}</label>
 | 
			
		||||
              <input type="checkbox" v-model="hideFollows" id="account-hide-follows">
 | 
			
		||||
              <label for="account-hide-follows">{{$t('settings.hide_follows_description')}}</label>
 | 
			
		||||
            </p>
 | 
			
		||||
            <p>
 | 
			
		||||
              <input
 | 
			
		||||
                id="account-hide-followers"
 | 
			
		||||
                v-model="hideFollowers"
 | 
			
		||||
                type="checkbox"
 | 
			
		||||
              >
 | 
			
		||||
              <label for="account-hide-followers">{{ $t('settings.hide_followers_description') }}</label>
 | 
			
		||||
              <input type="checkbox" v-model="hideFollowers" id="account-hide-followers">
 | 
			
		||||
              <label for="account-hide-followers">{{$t('settings.hide_followers_description')}}</label>
 | 
			
		||||
            </p>
 | 
			
		||||
            <p>
 | 
			
		||||
              <input
 | 
			
		||||
                id="account-show-role"
 | 
			
		||||
                v-model="showRole"
 | 
			
		||||
                type="checkbox"
 | 
			
		||||
              >
 | 
			
		||||
              <label
 | 
			
		||||
                v-if="role === 'admin'"
 | 
			
		||||
                for="account-show-role"
 | 
			
		||||
              >{{ $t('settings.show_admin_badge') }}</label>
 | 
			
		||||
              <label
 | 
			
		||||
                v-if="role === 'moderator'"
 | 
			
		||||
                for="account-show-role"
 | 
			
		||||
              >{{ $t('settings.show_moderator_badge') }}</label>
 | 
			
		||||
              <input type="checkbox" v-model="showRole" id="account-show-role">
 | 
			
		||||
              <label for="account-show-role" v-if="role === 'admin'">{{$t('settings.show_admin_badge')}}</label>
 | 
			
		||||
              <label for="account-show-role" v-if="role === 'moderator'">{{$t('settings.show_moderator_badge')}}</label>
 | 
			
		||||
            </p>
 | 
			
		||||
            <button
 | 
			
		||||
              :disabled="newName && newName.length === 0"
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
              @click="updateProfile"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('general.submit') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <button :disabled='newName && newName.length === 0' class="btn btn-default" @click="updateProfile">{{$t('general.submit')}}</button>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="setting-item">
 | 
			
		||||
            <h2>{{ $t('settings.avatar') }}</h2>
 | 
			
		||||
            <p class="visibility-notice">
 | 
			
		||||
              {{ $t('settings.avatar_size_instruction') }}
 | 
			
		||||
            </p>
 | 
			
		||||
            <p>{{ $t('settings.current_avatar') }}</p>
 | 
			
		||||
            <img
 | 
			
		||||
              :src="user.profile_image_url_original"
 | 
			
		||||
              class="current-avatar"
 | 
			
		||||
            >
 | 
			
		||||
            <p>{{ $t('settings.set_new_avatar') }}</p>
 | 
			
		||||
            <button
 | 
			
		||||
              v-show="pickAvatarBtnVisible"
 | 
			
		||||
              id="pick-avatar"
 | 
			
		||||
              class="btn"
 | 
			
		||||
              type="button"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.upload_a_photo') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <image-cropper
 | 
			
		||||
              trigger="#pick-avatar"
 | 
			
		||||
              :submit-handler="submitAvatar"
 | 
			
		||||
              @open="pickAvatarBtnVisible=false"
 | 
			
		||||
              @close="pickAvatarBtnVisible=true"
 | 
			
		||||
            />
 | 
			
		||||
            <h2>{{$t('settings.avatar')}}</h2>
 | 
			
		||||
            <p class="visibility-notice">{{$t('settings.avatar_size_instruction')}}</p>
 | 
			
		||||
            <p>{{$t('settings.current_avatar')}}</p>
 | 
			
		||||
            <img :src="user.profile_image_url_original" class="current-avatar" />
 | 
			
		||||
            <p>{{$t('settings.set_new_avatar')}}</p>
 | 
			
		||||
            <button class="btn" type="button" id="pick-avatar" v-show="pickAvatarBtnVisible">{{$t('settings.upload_a_photo')}}</button>
 | 
			
		||||
            <image-cropper trigger="#pick-avatar" :submitHandler="submitAvatar" @open="pickAvatarBtnVisible=false" @close="pickAvatarBtnVisible=true" />
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="setting-item">
 | 
			
		||||
            <h2>{{ $t('settings.profile_banner') }}</h2>
 | 
			
		||||
            <p>{{ $t('settings.current_profile_banner') }}</p>
 | 
			
		||||
            <img
 | 
			
		||||
              :src="user.cover_photo"
 | 
			
		||||
              class="banner"
 | 
			
		||||
            >
 | 
			
		||||
            <p>{{ $t('settings.set_new_profile_banner') }}</p>
 | 
			
		||||
            <img
 | 
			
		||||
              v-if="bannerPreview"
 | 
			
		||||
              class="banner"
 | 
			
		||||
              :src="bannerPreview"
 | 
			
		||||
            >
 | 
			
		||||
            <h2>{{$t('settings.profile_banner')}}</h2>
 | 
			
		||||
            <p>{{$t('settings.current_profile_banner')}}</p>
 | 
			
		||||
            <img :src="user.cover_photo" class="banner" />
 | 
			
		||||
            <p>{{$t('settings.set_new_profile_banner')}}</p>
 | 
			
		||||
            <img class="banner" v-bind:src="bannerPreview" v-if="bannerPreview" />
 | 
			
		||||
            <div>
 | 
			
		||||
              <input
 | 
			
		||||
                type="file"
 | 
			
		||||
                @change="uploadFile('banner', $event)"
 | 
			
		||||
              >
 | 
			
		||||
              <input type="file" @change="uploadFile('banner', $event)" />
 | 
			
		||||
            </div>
 | 
			
		||||
            <i
 | 
			
		||||
              v-if="bannerUploading"
 | 
			
		||||
              class=" icon-spin4 animate-spin uploading"
 | 
			
		||||
            />
 | 
			
		||||
            <button
 | 
			
		||||
              v-else-if="bannerPreview"
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
              @click="submitBanner"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('general.submit') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="bannerUploadError"
 | 
			
		||||
              class="alert error"
 | 
			
		||||
            >
 | 
			
		||||
            <i class=" icon-spin4 animate-spin uploading" v-if="bannerUploading"></i>
 | 
			
		||||
            <button class="btn btn-default" v-else-if="bannerPreview" @click="submitBanner">{{$t('general.submit')}}</button>
 | 
			
		||||
            <div class='alert error' v-if="bannerUploadError">
 | 
			
		||||
              Error: {{ bannerUploadError }}
 | 
			
		||||
              <i
 | 
			
		||||
                class="button-icon icon-cancel"
 | 
			
		||||
                @click="clearUploadError('banner')"
 | 
			
		||||
              />
 | 
			
		||||
              <i class="button-icon icon-cancel" @click="clearUploadError('banner')"></i>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div class="setting-item">
 | 
			
		||||
            <h2>{{ $t('settings.profile_background') }}</h2>
 | 
			
		||||
            <p>{{ $t('settings.set_new_profile_background') }}</p>
 | 
			
		||||
            <img
 | 
			
		||||
              v-if="backgroundPreview"
 | 
			
		||||
              class="bg"
 | 
			
		||||
              :src="backgroundPreview"
 | 
			
		||||
            >
 | 
			
		||||
            <h2>{{$t('settings.profile_background')}}</h2>
 | 
			
		||||
            <p>{{$t('settings.set_new_profile_background')}}</p>
 | 
			
		||||
            <img class="bg" v-bind:src="backgroundPreview" v-if="backgroundPreview" />
 | 
			
		||||
            <div>
 | 
			
		||||
              <input
 | 
			
		||||
                type="file"
 | 
			
		||||
                @change="uploadFile('background', $event)"
 | 
			
		||||
              >
 | 
			
		||||
              <input type="file" @change="uploadFile('background', $event)" />
 | 
			
		||||
            </div>
 | 
			
		||||
            <i
 | 
			
		||||
              v-if="backgroundUploading"
 | 
			
		||||
              class=" icon-spin4 animate-spin uploading"
 | 
			
		||||
            />
 | 
			
		||||
            <button
 | 
			
		||||
              v-else-if="backgroundPreview"
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
              @click="submitBg"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('general.submit') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <div
 | 
			
		||||
              v-if="backgroundUploadError"
 | 
			
		||||
              class="alert error"
 | 
			
		||||
            >
 | 
			
		||||
            <i class=" icon-spin4 animate-spin uploading" v-if="backgroundUploading"></i>
 | 
			
		||||
            <button class="btn btn-default" v-else-if="backgroundPreview" @click="submitBg">{{$t('general.submit')}}</button>
 | 
			
		||||
            <div class='alert error' v-if="backgroundUploadError">
 | 
			
		||||
              Error: {{ backgroundUploadError }}
 | 
			
		||||
              <i
 | 
			
		||||
                class="button-icon icon-cancel"
 | 
			
		||||
                @click="clearUploadError('background')"
 | 
			
		||||
              />
 | 
			
		||||
              <i class="button-icon icon-cancel" @click="clearUploadError('background')"></i>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div :label="$t('settings.security_tab')">
 | 
			
		||||
          <div class="setting-item">
 | 
			
		||||
            <h2>{{ $t('settings.change_password') }}</h2>
 | 
			
		||||
            <h2>{{$t('settings.change_password')}}</h2>
 | 
			
		||||
            <div>
 | 
			
		||||
              <p>{{ $t('settings.current_password') }}</p>
 | 
			
		||||
              <input
 | 
			
		||||
                v-model="changePasswordInputs[0]"
 | 
			
		||||
                type="password"
 | 
			
		||||
              >
 | 
			
		||||
              <p>{{$t('settings.current_password')}}</p>
 | 
			
		||||
              <input type="password" v-model="changePasswordInputs[0]">
 | 
			
		||||
            </div>
 | 
			
		||||
            <div>
 | 
			
		||||
              <p>{{ $t('settings.new_password') }}</p>
 | 
			
		||||
              <input
 | 
			
		||||
                v-model="changePasswordInputs[1]"
 | 
			
		||||
                type="password"
 | 
			
		||||
              >
 | 
			
		||||
              <p>{{$t('settings.new_password')}}</p>
 | 
			
		||||
              <input type="password" v-model="changePasswordInputs[1]">
 | 
			
		||||
            </div>
 | 
			
		||||
            <div>
 | 
			
		||||
              <p>{{ $t('settings.confirm_new_password') }}</p>
 | 
			
		||||
              <input
 | 
			
		||||
                v-model="changePasswordInputs[2]"
 | 
			
		||||
                type="password"
 | 
			
		||||
              >
 | 
			
		||||
              <p>{{$t('settings.confirm_new_password')}}</p>
 | 
			
		||||
              <input type="password" v-model="changePasswordInputs[2]">
 | 
			
		||||
            </div>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
              @click="changePassword"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('general.submit') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <p v-if="changedPassword">
 | 
			
		||||
              {{ $t('settings.changed_password') }}
 | 
			
		||||
            </p>
 | 
			
		||||
            <p v-else-if="changePasswordError !== false">
 | 
			
		||||
              {{ $t('settings.change_password_error') }}
 | 
			
		||||
            </p>
 | 
			
		||||
            <p v-if="changePasswordError">
 | 
			
		||||
              {{ changePasswordError }}
 | 
			
		||||
            </p>
 | 
			
		||||
            <button class="btn btn-default" @click="changePassword">{{$t('general.submit')}}</button>
 | 
			
		||||
            <p v-if="changedPassword">{{$t('settings.changed_password')}}</p>
 | 
			
		||||
            <p v-else-if="changePasswordError !== false">{{$t('settings.change_password_error')}}</p>
 | 
			
		||||
            <p v-if="changePasswordError">{{changePasswordError}}</p>
 | 
			
		||||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div class="setting-item">
 | 
			
		||||
            <h2>{{ $t('settings.oauth_tokens') }}</h2>
 | 
			
		||||
            <h2>{{$t('settings.oauth_tokens')}}</h2>
 | 
			
		||||
            <table class="oauth-tokens">
 | 
			
		||||
              <thead>
 | 
			
		||||
                <tr>
 | 
			
		||||
                  <th>{{ $t('settings.app_name') }}</th>
 | 
			
		||||
                  <th>{{ $t('settings.valid_until') }}</th>
 | 
			
		||||
                  <th />
 | 
			
		||||
                  <th>{{$t('settings.app_name')}}</th>
 | 
			
		||||
                  <th>{{$t('settings.valid_until')}}</th>
 | 
			
		||||
                  <th></th>
 | 
			
		||||
                </tr>
 | 
			
		||||
              </thead>
 | 
			
		||||
              <tbody>
 | 
			
		||||
                <tr
 | 
			
		||||
                  v-for="oauthToken in oauthTokens"
 | 
			
		||||
                  :key="oauthToken.id"
 | 
			
		||||
                >
 | 
			
		||||
                  <td>{{ oauthToken.appName }}</td>
 | 
			
		||||
                  <td>{{ oauthToken.validUntil }}</td>
 | 
			
		||||
                <tr v-for="oauthToken in oauthTokens" :key="oauthToken.id">
 | 
			
		||||
                  <td>{{oauthToken.appName}}</td>
 | 
			
		||||
                  <td>{{oauthToken.validUntil}}</td>
 | 
			
		||||
                  <td class="actions">
 | 
			
		||||
                    <button
 | 
			
		||||
                      class="btn btn-default"
 | 
			
		||||
                      @click="revokeToken(oauthToken.id)"
 | 
			
		||||
                    >
 | 
			
		||||
                      {{ $t('settings.revoke_token') }}
 | 
			
		||||
                    <button class="btn btn-default" @click="revokeToken(oauthToken.id)">
 | 
			
		||||
                      {{$t('settings.revoke_token')}}
 | 
			
		||||
                    </button>
 | 
			
		||||
                  </td>
 | 
			
		||||
                </tr>
 | 
			
		||||
| 
						 | 
				
			
			@ -287,113 +153,56 @@
 | 
			
		|||
          </div>
 | 
			
		||||
 | 
			
		||||
          <div class="setting-item">
 | 
			
		||||
            <h2>{{ $t('settings.delete_account') }}</h2>
 | 
			
		||||
            <p v-if="!deletingAccount">
 | 
			
		||||
              {{ $t('settings.delete_account_description') }}
 | 
			
		||||
            </p>
 | 
			
		||||
            <h2>{{$t('settings.delete_account')}}</h2>
 | 
			
		||||
            <p v-if="!deletingAccount">{{$t('settings.delete_account_description')}}</p>
 | 
			
		||||
            <div v-if="deletingAccount">
 | 
			
		||||
              <p>{{ $t('settings.delete_account_instructions') }}</p>
 | 
			
		||||
              <p>{{ $t('login.password') }}</p>
 | 
			
		||||
              <input
 | 
			
		||||
                v-model="deleteAccountConfirmPasswordInput"
 | 
			
		||||
                type="password"
 | 
			
		||||
              >
 | 
			
		||||
              <button
 | 
			
		||||
                class="btn btn-default"
 | 
			
		||||
                @click="deleteAccount"
 | 
			
		||||
              >
 | 
			
		||||
                {{ $t('settings.delete_account') }}
 | 
			
		||||
              </button>
 | 
			
		||||
              <p>{{$t('settings.delete_account_instructions')}}</p>
 | 
			
		||||
              <p>{{$t('login.password')}}</p>
 | 
			
		||||
              <input type="password" v-model="deleteAccountConfirmPasswordInput">
 | 
			
		||||
              <button class="btn btn-default" @click="deleteAccount">{{$t('settings.delete_account')}}</button>
 | 
			
		||||
            </div>
 | 
			
		||||
            <p v-if="deleteAccountError !== false">
 | 
			
		||||
              {{ $t('settings.delete_account_error') }}
 | 
			
		||||
            </p>
 | 
			
		||||
            <p v-if="deleteAccountError">
 | 
			
		||||
              {{ deleteAccountError }}
 | 
			
		||||
            </p>
 | 
			
		||||
            <button
 | 
			
		||||
              v-if="!deletingAccount"
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
              @click="confirmDelete"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('general.submit') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <p v-if="deleteAccountError !== false">{{$t('settings.delete_account_error')}}</p>
 | 
			
		||||
            <p v-if="deleteAccountError">{{deleteAccountError}}</p>
 | 
			
		||||
            <button class="btn btn-default" v-if="!deletingAccount" @click="confirmDelete">{{$t('general.submit')}}</button>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div
 | 
			
		||||
          v-if="pleromaBackend"
 | 
			
		||||
          :label="$t('settings.data_import_export_tab')"
 | 
			
		||||
        >
 | 
			
		||||
        <div :label="$t('settings.data_import_export_tab')" v-if="pleromaBackend">
 | 
			
		||||
          <div class="setting-item">
 | 
			
		||||
            <h2>{{ $t('settings.follow_import') }}</h2>
 | 
			
		||||
            <p>{{ $t('settings.import_followers_from_a_csv_file') }}</p>
 | 
			
		||||
            <h2>{{$t('settings.follow_import')}}</h2>
 | 
			
		||||
            <p>{{$t('settings.import_followers_from_a_csv_file')}}</p>
 | 
			
		||||
            <form>
 | 
			
		||||
              <input
 | 
			
		||||
                ref="followlist"
 | 
			
		||||
                type="file"
 | 
			
		||||
                @change="followListChange"
 | 
			
		||||
              >
 | 
			
		||||
              <input type="file" ref="followlist" v-on:change="followListChange" />
 | 
			
		||||
            </form>
 | 
			
		||||
            <i
 | 
			
		||||
              v-if="followListUploading"
 | 
			
		||||
              class=" icon-spin4 animate-spin uploading"
 | 
			
		||||
            />
 | 
			
		||||
            <button
 | 
			
		||||
              v-else
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
              @click="importFollows"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('general.submit') }}
 | 
			
		||||
            </button>
 | 
			
		||||
            <i class=" icon-spin4 animate-spin uploading" v-if="followListUploading"></i>
 | 
			
		||||
            <button class="btn btn-default" v-else @click="importFollows">{{$t('general.submit')}}</button>
 | 
			
		||||
            <div v-if="followsImported">
 | 
			
		||||
              <i
 | 
			
		||||
                class="icon-cross"
 | 
			
		||||
                @click="dismissImported"
 | 
			
		||||
              />
 | 
			
		||||
              <p>{{ $t('settings.follows_imported') }}</p>
 | 
			
		||||
              <i class="icon-cross" @click="dismissImported"></i>
 | 
			
		||||
              <p>{{$t('settings.follows_imported')}}</p>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div v-else-if="followImportError">
 | 
			
		||||
              <i
 | 
			
		||||
                class="icon-cross"
 | 
			
		||||
                @click="dismissImported"
 | 
			
		||||
              />
 | 
			
		||||
              <p>{{ $t('settings.follow_import_error') }}</p>
 | 
			
		||||
              <i class="icon-cross" @click="dismissImported"></i>
 | 
			
		||||
              <p>{{$t('settings.follow_import_error')}}</p>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div
 | 
			
		||||
            v-if="enableFollowsExport"
 | 
			
		||||
            class="setting-item"
 | 
			
		||||
          >
 | 
			
		||||
            <h2>{{ $t('settings.follow_export') }}</h2>
 | 
			
		||||
            <button
 | 
			
		||||
              class="btn btn-default"
 | 
			
		||||
              @click="exportFollows"
 | 
			
		||||
            >
 | 
			
		||||
              {{ $t('settings.follow_export_button') }}
 | 
			
		||||
            </button>
 | 
			
		||||
          <div class="setting-item" v-if="enableFollowsExport">
 | 
			
		||||
            <h2>{{$t('settings.follow_export')}}</h2>
 | 
			
		||||
            <button class="btn btn-default" @click="exportFollows">{{$t('settings.follow_export_button')}}</button>
 | 
			
		||||
          </div>
 | 
			
		||||
          <div
 | 
			
		||||
            v-else
 | 
			
		||||
            class="setting-item"
 | 
			
		||||
          >
 | 
			
		||||
            <h2>{{ $t('settings.follow_export_processing') }}</h2>
 | 
			
		||||
          <div class="setting-item" v-else>
 | 
			
		||||
            <h2>{{$t('settings.follow_export_processing')}}</h2>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div :label="$t('settings.blocks_tab')">
 | 
			
		||||
          <block-list :refresh="true">
 | 
			
		||||
            <template slot="empty">
 | 
			
		||||
              {{ $t('settings.no_blocks') }}
 | 
			
		||||
            </template>
 | 
			
		||||
            <template slot="empty">{{$t('settings.no_blocks')}}</template>
 | 
			
		||||
          </block-list>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div :label="$t('settings.mutes_tab')">
 | 
			
		||||
          <mute-list :refresh="true">
 | 
			
		||||
            <template slot="empty">
 | 
			
		||||
              {{ $t('settings.no_mutes') }}
 | 
			
		||||
            </template>
 | 
			
		||||
            <template slot="empty">{{$t('settings.no_mutes')}}</template>
 | 
			
		||||
          </mute-list>
 | 
			
		||||
        </div>
 | 
			
		||||
      </tab-switcher>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,11 +1,10 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <video
 | 
			
		||||
    class="video"
 | 
			
		||||
  <video class="video"
 | 
			
		||||
    @loadeddata="onVideoDataLoad"
 | 
			
		||||
    :src="attachment.url"
 | 
			
		||||
    :loop="loopVideo"
 | 
			
		||||
    :controls="controls"
 | 
			
		||||
    playsinline
 | 
			
		||||
    @loadeddata="onVideoDataLoad"
 | 
			
		||||
  />
 | 
			
		||||
</template>
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -36,7 +36,7 @@ const WhoToFollow = {
 | 
			
		|||
    getWhoToFollow () {
 | 
			
		||||
      const credentials = this.$store.state.users.currentUser.credentials
 | 
			
		||||
      if (credentials) {
 | 
			
		||||
        apiService.suggestions({ credentials: credentials })
 | 
			
		||||
        apiService.suggestions({credentials: credentials})
 | 
			
		||||
          .then((reply) => {
 | 
			
		||||
            this.showWhoToFollow(reply)
 | 
			
		||||
          })
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,14 +1,10 @@
 | 
			
		|||
<template>
 | 
			
		||||
  <div class="panel panel-default">
 | 
			
		||||
    <div class="panel-heading">
 | 
			
		||||
      {{ $t('who_to_follow.who_to_follow') }}
 | 
			
		||||
      {{$t('who_to_follow.who_to_follow')}}
 | 
			
		||||
    </div>
 | 
			
		||||
    <div class="panel-body">
 | 
			
		||||
      <FollowCard
 | 
			
		||||
        v-for="user in users"
 | 
			
		||||
        :key="user.id"
 | 
			
		||||
        :user="user"
 | 
			
		||||
      />
 | 
			
		||||
      <FollowCard v-for="user in users" :key="user.id" :user="user"/>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
</template>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -29,7 +29,7 @@ function getWhoToFollow (panel) {
 | 
			
		|||
    panel.usersToFollow.forEach(toFollow => {
 | 
			
		||||
      toFollow.name = 'Loading...'
 | 
			
		||||
    })
 | 
			
		||||
    apiService.suggestions({ credentials: credentials })
 | 
			
		||||
    apiService.suggestions({credentials: credentials})
 | 
			
		||||
      .then((reply) => {
 | 
			
		||||
        showWhoToFollow(panel, reply)
 | 
			
		||||
      })
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -3,22 +3,17 @@
 | 
			
		|||
    <div class="panel panel-default base01-background">
 | 
			
		||||
      <div class="panel-heading timeline-heading base02-background base04">
 | 
			
		||||
        <div class="title">
 | 
			
		||||
          {{ $t('who_to_follow.who_to_follow') }}
 | 
			
		||||
          {{$t('who_to_follow.who_to_follow')}}
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="panel-body who-to-follow">
 | 
			
		||||
        <span
 | 
			
		||||
          v-for="user in usersToFollow"
 | 
			
		||||
          :key="user.id"
 | 
			
		||||
        >
 | 
			
		||||
          <img :src="user.img">
 | 
			
		||||
          <router-link :to="userProfileLink(user.id, user.name)">
 | 
			
		||||
            {{ user.name }}
 | 
			
		||||
          </router-link><br>
 | 
			
		||||
        <span v-for="user in usersToFollow">
 | 
			
		||||
          <img v-bind:src="user.img" />
 | 
			
		||||
            <router-link v-bind:to="userProfileLink(user.id, user.name)">
 | 
			
		||||
              {{user.name}}
 | 
			
		||||
            </router-link><br />
 | 
			
		||||
        </span>
 | 
			
		||||
        <img :src="$store.state.instance.logo"> <router-link :to="{ name: 'who-to-follow' }">
 | 
			
		||||
          {{ $t('who_to_follow.more') }}
 | 
			
		||||
        </router-link>
 | 
			
		||||
        <img v-bind:src="$store.state.instance.logo"> <router-link :to="{ name: 'who-to-follow' }">{{$t('who_to_follow.more')}}</router-link>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
  </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -7,14 +7,14 @@ const defaultEntryPropsGetter = entry => ({ entry })
 | 
			
		|||
const defaultKeyGetter = entry => entry.id
 | 
			
		||||
 | 
			
		||||
const withList = ({
 | 
			
		||||
  getEntryProps = defaultEntryPropsGetter, // function to accept entry and index values and return props to be passed into the item component
 | 
			
		||||
  getKey = defaultKeyGetter // funciton to accept entry and index values and return key prop value
 | 
			
		||||
  getEntryProps = defaultEntryPropsGetter,  // function to accept entry and index values and return props to be passed into the item component
 | 
			
		||||
  getKey = defaultKeyGetter                 // funciton to accept entry and index values and return key prop value
 | 
			
		||||
}) => (ItemComponent) => (
 | 
			
		||||
  Vue.component('withList', {
 | 
			
		||||
    props: [
 | 
			
		||||
      'entries', // array of entry
 | 
			
		||||
      'entryProps', // additional props to be passed into each entry
 | 
			
		||||
      'entryListeners' // additional event listeners to be passed into each entry
 | 
			
		||||
      'entries',                            // array of entry
 | 
			
		||||
      'entryProps',                         // additional props to be passed into each entry
 | 
			
		||||
      'entryListeners'                      // additional event listeners to be passed into each entry
 | 
			
		||||
    ],
 | 
			
		||||
    render (createElement) {
 | 
			
		||||
      return (
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -4,16 +4,39 @@ import { getComponentProps } from '../../services/component_utils/component_util
 | 
			
		|||
import './with_load_more.scss'
 | 
			
		||||
 | 
			
		||||
const withLoadMore = ({
 | 
			
		||||
  fetch, // function to fetch entries and return a promise
 | 
			
		||||
  select, // function to select data from store
 | 
			
		||||
  destroy, // function called at "destroyed" lifecycle
 | 
			
		||||
  childPropName = 'entries', // name of the prop to be passed into the wrapped component
 | 
			
		||||
  additionalPropNames = [] // additional prop name list of the wrapper component
 | 
			
		||||
  fetch,                      // function to fetch entries and return a promise
 | 
			
		||||
  select,                     // function to select data from store
 | 
			
		||||
  destroy,                    // function called at "destroyed" lifecycle
 | 
			
		||||
  childPropName = 'entries',  // name of the prop to be passed into the wrapped component
 | 
			
		||||
  additionalPropNames = []    // additional prop name list of the wrapper component
 | 
			
		||||
}) => (WrappedComponent) => {
 | 
			
		||||
  const originalProps = Object.keys(getComponentProps(WrappedComponent))
 | 
			
		||||
  const props = originalProps.filter(v => v !== childPropName).concat(additionalPropNames)
 | 
			
		||||
 | 
			
		||||
  return Vue.component('withLoadMore', {
 | 
			
		||||
    render (createElement) {
 | 
			
		||||
      const props = {
 | 
			
		||||
        props: {
 | 
			
		||||
          ...this.$props,
 | 
			
		||||
          [childPropName]: this.entries
 | 
			
		||||
        },
 | 
			
		||||
        on: this.$listeners,
 | 
			
		||||
        scopedSlots: this.$scopedSlots
 | 
			
		||||
      }
 | 
			
		||||
      const children = Object.entries(this.$slots).map(([key, value]) => createElement('template', { slot: key }, value))
 | 
			
		||||
      return (
 | 
			
		||||
        <div class="with-load-more">
 | 
			
		||||
          <WrappedComponent {...props}>
 | 
			
		||||
            {children}
 | 
			
		||||
          </WrappedComponent>
 | 
			
		||||
          <div class="with-load-more-footer">
 | 
			
		||||
            {this.error && <a onClick={this.fetchEntries} class="alert error">{this.$t('general.generic_error')}</a>}
 | 
			
		||||
            {!this.error && this.loading && <i class="icon-spin3 animate-spin"/>}
 | 
			
		||||
            {!this.error && !this.loading && !this.bottomedOut && <a onClick={this.fetchEntries}>{this.$t('general.more')}</a>}
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      )
 | 
			
		||||
    },
 | 
			
		||||
    props,
 | 
			
		||||
    data () {
 | 
			
		||||
      return {
 | 
			
		||||
| 
						 | 
				
			
			@ -64,29 +87,6 @@ const withLoadMore = ({
 | 
			
		|||
          this.fetchEntries()
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    render (createElement) {
 | 
			
		||||
      const props = {
 | 
			
		||||
        props: {
 | 
			
		||||
          ...this.$props,
 | 
			
		||||
          [childPropName]: this.entries
 | 
			
		||||
        },
 | 
			
		||||
        on: this.$listeners,
 | 
			
		||||
        scopedSlots: this.$scopedSlots
 | 
			
		||||
      }
 | 
			
		||||
      const children = Object.entries(this.$slots).map(([key, value]) => createElement('template', { slot: key }, value))
 | 
			
		||||
      return (
 | 
			
		||||
        <div class="with-load-more">
 | 
			
		||||
          <WrappedComponent {...props}>
 | 
			
		||||
            {children}
 | 
			
		||||
          </WrappedComponent>
 | 
			
		||||
          <div class="with-load-more-footer">
 | 
			
		||||
            {this.error && <a onClick={this.fetchEntries} class="alert error">{this.$t('general.generic_error')}</a>}
 | 
			
		||||
            {!this.error && this.loading && <i class="icon-spin3 animate-spin"/>}
 | 
			
		||||
            {!this.error && !this.loading && !this.bottomedOut && <a onClick={this.fetchEntries}>{this.$t('general.more')}</a>}
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      )
 | 
			
		||||
    }
 | 
			
		||||
  })
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -4,10 +4,10 @@ import { getComponentProps } from '../../services/component_utils/component_util
 | 
			
		|||
import './with_subscription.scss'
 | 
			
		||||
 | 
			
		||||
const withSubscription = ({
 | 
			
		||||
  fetch, // function to fetch entries and return a promise
 | 
			
		||||
  select, // function to select data from store
 | 
			
		||||
  childPropName = 'content', // name of the prop to be passed into the wrapped component
 | 
			
		||||
  additionalPropNames = [] // additional prop name list of the wrapper component
 | 
			
		||||
  fetch,                      // function to fetch entries and return a promise
 | 
			
		||||
  select,                     // function to select data from store
 | 
			
		||||
  childPropName = 'content',  // name of the prop to be passed into the wrapped component
 | 
			
		||||
  additionalPropNames = []    // additional prop name list of the wrapper component
 | 
			
		||||
}) => (WrappedComponent) => {
 | 
			
		||||
  const originalProps = Object.keys(getComponentProps(WrappedComponent))
 | 
			
		||||
  const props = originalProps.filter(v => v !== childPropName).concat(additionalPropNames)
 | 
			
		||||
| 
						 | 
				
			
			@ -15,8 +15,37 @@ const withSubscription = ({
 | 
			
		|||
  return Vue.component('withSubscription', {
 | 
			
		||||
    props: [
 | 
			
		||||
      ...props,
 | 
			
		||||
      'refresh' // boolean saying to force-fetch data whenever created
 | 
			
		||||
      'refresh'               // boolean saying to force-fetch data whenever created
 | 
			
		||||
    ],
 | 
			
		||||
    render (createElement) {
 | 
			
		||||
      if (!this.error && !this.loading) {
 | 
			
		||||
        const props = {
 | 
			
		||||
          props: {
 | 
			
		||||
            ...this.$props,
 | 
			
		||||
            [childPropName]: this.fetchedData
 | 
			
		||||
          },
 | 
			
		||||
          on: this.$listeners,
 | 
			
		||||
          scopedSlots: this.$scopedSlots
 | 
			
		||||
        }
 | 
			
		||||
        const children = Object.entries(this.$slots).map(([key, value]) => createElement('template', { slot: key }, value))
 | 
			
		||||
        return (
 | 
			
		||||
          <div class="with-subscription">
 | 
			
		||||
            <WrappedComponent {...props}>
 | 
			
		||||
              {children}
 | 
			
		||||
            </WrappedComponent>
 | 
			
		||||
          </div>
 | 
			
		||||
        )
 | 
			
		||||
      } else {
 | 
			
		||||
        return (
 | 
			
		||||
          <div class="with-subscription-loading">
 | 
			
		||||
            {this.error
 | 
			
		||||
              ? <a onClick={this.fetchData} class="alert error">{this.$t('general.generic_error')}</a>
 | 
			
		||||
              : <i class="icon-spin3 animate-spin"/>
 | 
			
		||||
            }
 | 
			
		||||
          </div>
 | 
			
		||||
        )
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    data () {
 | 
			
		||||
      return {
 | 
			
		||||
        loading: false,
 | 
			
		||||
| 
						 | 
				
			
			@ -48,35 +77,6 @@ const withSubscription = ({
 | 
			
		|||
            })
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    render (createElement) {
 | 
			
		||||
      if (!this.error && !this.loading) {
 | 
			
		||||
        const props = {
 | 
			
		||||
          props: {
 | 
			
		||||
            ...this.$props,
 | 
			
		||||
            [childPropName]: this.fetchedData
 | 
			
		||||
          },
 | 
			
		||||
          on: this.$listeners,
 | 
			
		||||
          scopedSlots: this.$scopedSlots
 | 
			
		||||
        }
 | 
			
		||||
        const children = Object.entries(this.$slots).map(([key, value]) => createElement('template', { slot: key }, value))
 | 
			
		||||
        return (
 | 
			
		||||
          <div class="with-subscription">
 | 
			
		||||
            <WrappedComponent {...props}>
 | 
			
		||||
              {children}
 | 
			
		||||
            </WrappedComponent>
 | 
			
		||||
          </div>
 | 
			
		||||
        )
 | 
			
		||||
      } else {
 | 
			
		||||
        return (
 | 
			
		||||
          <div class="with-subscription-loading">
 | 
			
		||||
            {this.error
 | 
			
		||||
              ? <a onClick={this.fetchData} class="alert error">{this.$t('general.generic_error')}</a>
 | 
			
		||||
              : <i class="icon-spin3 animate-spin"/>
 | 
			
		||||
            }
 | 
			
		||||
          </div>
 | 
			
		||||
        )
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  })
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -13,10 +13,10 @@ const api = {
 | 
			
		|||
    setBackendInteractor (state, backendInteractor) {
 | 
			
		||||
      state.backendInteractor = backendInteractor
 | 
			
		||||
    },
 | 
			
		||||
    addFetcher (state, { timeline, fetcher }) {
 | 
			
		||||
    addFetcher (state, {timeline, fetcher}) {
 | 
			
		||||
      state.fetchers[timeline] = fetcher
 | 
			
		||||
    },
 | 
			
		||||
    removeFetcher (state, { timeline }) {
 | 
			
		||||
    removeFetcher (state, {timeline}) {
 | 
			
		||||
      delete state.fetchers[timeline]
 | 
			
		||||
    },
 | 
			
		||||
    setWsToken (state, token) {
 | 
			
		||||
| 
						 | 
				
			
			@ -33,7 +33,7 @@ const api = {
 | 
			
		|||
    }
 | 
			
		||||
  },
 | 
			
		||||
  actions: {
 | 
			
		||||
    startFetching (store, { timeline = 'friends', tag = false, userId = false }) {
 | 
			
		||||
    startFetching (store, {timeline = 'friends', tag = false, userId = false}) {
 | 
			
		||||
      // Don't start fetching if we already are.
 | 
			
		||||
      if (store.state.fetchers[timeline]) return
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -43,7 +43,7 @@ const api = {
 | 
			
		|||
    stopFetching (store, timeline) {
 | 
			
		||||
      const fetcher = store.state.fetchers[timeline]
 | 
			
		||||
      window.clearInterval(fetcher)
 | 
			
		||||
      store.commit('removeFetcher', { timeline })
 | 
			
		||||
      store.commit('removeFetcher', {timeline})
 | 
			
		||||
    },
 | 
			
		||||
    setWsToken (store, token) {
 | 
			
		||||
      store.commit('setWsToken', token)
 | 
			
		||||
| 
						 | 
				
			
			@ -52,7 +52,7 @@ const api = {
 | 
			
		|||
      // Set up websocket connection
 | 
			
		||||
      if (!store.state.chatDisabled) {
 | 
			
		||||
        const token = store.state.wsToken
 | 
			
		||||
        const socket = new Socket('/socket', { params: { token } })
 | 
			
		||||
        const socket = new Socket('/socket', {params: {token}})
 | 
			
		||||
        socket.connect()
 | 
			
		||||
        store.dispatch('initializeChat', socket)
 | 
			
		||||
      }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,7 +1,7 @@
 | 
			
		|||
const chat = {
 | 
			
		||||
  state: {
 | 
			
		||||
    messages: [],
 | 
			
		||||
    channel: { state: '' },
 | 
			
		||||
    channel: {state: ''},
 | 
			
		||||
    socket: null
 | 
			
		||||
  },
 | 
			
		||||
  mutations: {
 | 
			
		||||
| 
						 | 
				
			
			@ -29,7 +29,7 @@ const chat = {
 | 
			
		|||
      channel.on('new_msg', (msg) => {
 | 
			
		||||
        store.commit('addMessage', msg)
 | 
			
		||||
      })
 | 
			
		||||
      channel.on('messages', ({ messages }) => {
 | 
			
		||||
      channel.on('messages', ({messages}) => {
 | 
			
		||||
        store.commit('setMessages', messages)
 | 
			
		||||
      })
 | 
			
		||||
      channel.join()
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -54,10 +54,10 @@ const config = {
 | 
			
		|||
  },
 | 
			
		||||
  actions: {
 | 
			
		||||
    setHighlight ({ commit, dispatch }, { user, color, type }) {
 | 
			
		||||
      commit('setHighlight', { user, color, type })
 | 
			
		||||
      commit('setHighlight', {user, color, type})
 | 
			
		||||
    },
 | 
			
		||||
    setOption ({ commit, dispatch }, { name, value }) {
 | 
			
		||||
      commit('setOption', { name, value })
 | 
			
		||||
      commit('setOption', {name, value})
 | 
			
		||||
      switch (name) {
 | 
			
		||||
        case 'theme':
 | 
			
		||||
          setPreset(value, commit)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -9,3 +9,4 @@ export function humanizeErrors (errors) {
 | 
			
		|||
    return [...errs, message]
 | 
			
		||||
  }, [])
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -68,7 +68,7 @@ const instance = {
 | 
			
		|||
  },
 | 
			
		||||
  actions: {
 | 
			
		||||
    setInstanceOption ({ commit, dispatch }, { name, value }) {
 | 
			
		||||
      commit('setInstanceOption', { name, value })
 | 
			
		||||
      commit('setInstanceOption', {name, value})
 | 
			
		||||
      switch (name) {
 | 
			
		||||
        case 'name':
 | 
			
		||||
          dispatch('setPageTitle')
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -3,12 +3,12 @@ const oauthTokens = {
 | 
			
		|||
    tokens: []
 | 
			
		||||
  },
 | 
			
		||||
  actions: {
 | 
			
		||||
    fetchTokens ({ rootState, commit }) {
 | 
			
		||||
    fetchTokens ({rootState, commit}) {
 | 
			
		||||
      rootState.api.backendInteractor.fetchOAuthTokens().then((tokens) => {
 | 
			
		||||
        commit('swapTokens', tokens)
 | 
			
		||||
      })
 | 
			
		||||
    },
 | 
			
		||||
    revokeToken ({ rootState, commit, state }, id) {
 | 
			
		||||
    revokeToken ({rootState, commit, state}, id) {
 | 
			
		||||
      rootState.api.backendInteractor.revokeOAuthToken(id).then((response) => {
 | 
			
		||||
        if (response.status === 201) {
 | 
			
		||||
          commit('swapTokens', state.tokens.filter(token => token.id !== id))
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -78,13 +78,13 @@ const mergeOrAdd = (arr, obj, item) => {
 | 
			
		|||
    merge(oldItem, omitBy(item, (v, k) => v === null || k === 'user'))
 | 
			
		||||
    // Reactivity fix.
 | 
			
		||||
    oldItem.attachments.splice(oldItem.attachments.length)
 | 
			
		||||
    return { item: oldItem, new: false }
 | 
			
		||||
    return {item: oldItem, new: false}
 | 
			
		||||
  } else {
 | 
			
		||||
    // This is a new item, prepare it
 | 
			
		||||
    prepareStatus(item)
 | 
			
		||||
    arr.push(item)
 | 
			
		||||
    set(obj, item.id, item)
 | 
			
		||||
    return { item, new: true }
 | 
			
		||||
    return {item, new: true}
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -237,12 +237,12 @@ const addNewStatuses = (state, { statuses, showImmediately = false, timeline, us
 | 
			
		|||
      const uri = deletion.uri
 | 
			
		||||
 | 
			
		||||
      // Remove possible notification
 | 
			
		||||
      const status = find(allStatuses, { uri })
 | 
			
		||||
      const status = find(allStatuses, {uri})
 | 
			
		||||
      if (!status) {
 | 
			
		||||
        return
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      remove(state.notifications.data, ({ action: { id } }) => id === status.id)
 | 
			
		||||
      remove(state.notifications.data, ({action: {id}}) => id === status.id)
 | 
			
		||||
 | 
			
		||||
      remove(allStatuses, { uri })
 | 
			
		||||
      if (timeline) {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -224,8 +224,8 @@ const users = {
 | 
			
		|||
          .then((friends) => {
 | 
			
		||||
            commit('addFriends', { id: user.id, friends })
 | 
			
		||||
            resolve(friends)
 | 
			
		||||
          }).catch(e => {
 | 
			
		||||
            reject(e)
 | 
			
		||||
          }).catch(() => {
 | 
			
		||||
            reject()
 | 
			
		||||
          })
 | 
			
		||||
      })
 | 
			
		||||
    },
 | 
			
		||||
| 
						 | 
				
			
			@ -279,8 +279,8 @@ const users = {
 | 
			
		|||
 | 
			
		||||
      const notificationsObject = store.rootState.statuses.notifications.idStore
 | 
			
		||||
      const relevantNotifications = Object.entries(notificationsObject)
 | 
			
		||||
        .filter(([k, val]) => notificationIds.includes(k))
 | 
			
		||||
        .map(([k, val]) => val)
 | 
			
		||||
            .filter(([k, val]) => notificationIds.includes(k))
 | 
			
		||||
            .map(([k, val]) => val)
 | 
			
		||||
 | 
			
		||||
      // Reconnect users to notifications
 | 
			
		||||
      each(relevantNotifications, (notification) => {
 | 
			
		||||
| 
						 | 
				
			
			@ -322,7 +322,7 @@ const users = {
 | 
			
		|||
      }
 | 
			
		||||
    },
 | 
			
		||||
    async getCaptcha (store) {
 | 
			
		||||
      return store.rootState.api.backendInteractor.getCaptcha()
 | 
			
		||||
      return await store.rootState.api.backendInteractor.getCaptcha()
 | 
			
		||||
    },
 | 
			
		||||
 | 
			
		||||
    logout (store) {
 | 
			
		||||
| 
						 | 
				
			
			@ -376,19 +376,19 @@ const users = {
 | 
			
		|||
              // Authentication failed
 | 
			
		||||
              commit('endLogin')
 | 
			
		||||
              if (response.status === 401) {
 | 
			
		||||
                reject(new Error('Wrong username or password'))
 | 
			
		||||
                reject('Wrong username or password')
 | 
			
		||||
              } else {
 | 
			
		||||
                reject(new Error('An error occurred, please try again'))
 | 
			
		||||
                reject('An error occurred, please try again')
 | 
			
		||||
              }
 | 
			
		||||
            }
 | 
			
		||||
            commit('endLogin')
 | 
			
		||||
            resolve()
 | 
			
		||||
          })
 | 
			
		||||
          .catch((error) => {
 | 
			
		||||
            console.log(error)
 | 
			
		||||
            commit('endLogin')
 | 
			
		||||
            reject(new Error('Failed to connect to server, try again'))
 | 
			
		||||
          })
 | 
			
		||||
        .catch((error) => {
 | 
			
		||||
          console.log(error)
 | 
			
		||||
          commit('endLogin')
 | 
			
		||||
          reject('Failed to connect to server, try again')
 | 
			
		||||
        })
 | 
			
		||||
      })
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,9 +1,4 @@
 | 
			
		|||
/* eslint-env browser */
 | 
			
		||||
import { each, map } from 'lodash'
 | 
			
		||||
import { parseStatus, parseUser, parseNotification, parseAttachment } from '../entity_normalizer/entity_normalizer.service.js'
 | 
			
		||||
import 'whatwg-fetch'
 | 
			
		||||
import { StatusCodeError } from '../errors/errors'
 | 
			
		||||
 | 
			
		||||
const LOGIN_URL = '/api/account/verify_credentials.json'
 | 
			
		||||
const ALL_FOLLOWING_URL = '/api/qvitter/allfollowing'
 | 
			
		||||
const MENTIONS_URL = '/api/statuses/mentions.json'
 | 
			
		||||
| 
						 | 
				
			
			@ -51,6 +46,11 @@ const MASTODON_UNMUTE_USER_URL = id => `/api/v1/accounts/${id}/unmute`
 | 
			
		|||
const MASTODON_POST_STATUS_URL = '/api/v1/statuses'
 | 
			
		||||
const MASTODON_MEDIA_UPLOAD_URL = '/api/v1/media'
 | 
			
		||||
 | 
			
		||||
import { each, map } from 'lodash'
 | 
			
		||||
import { parseStatus, parseUser, parseNotification, parseAttachment } from '../entity_normalizer/entity_normalizer.service.js'
 | 
			
		||||
import 'whatwg-fetch'
 | 
			
		||||
import { StatusCodeError } from '../errors/errors'
 | 
			
		||||
 | 
			
		||||
const oldfetch = window.fetch
 | 
			
		||||
 | 
			
		||||
let fetch = (url, options) => {
 | 
			
		||||
| 
						 | 
				
			
			@ -80,7 +80,7 @@ const promisedRequest = (url, options) => {
 | 
			
		|||
// cropX
 | 
			
		||||
// cropY
 | 
			
		||||
// img (base 64 encodend data url)
 | 
			
		||||
const updateAvatar = ({ credentials, params }) => {
 | 
			
		||||
const updateAvatar = ({credentials, params}) => {
 | 
			
		||||
  let url = AVATAR_UPDATE_URL
 | 
			
		||||
 | 
			
		||||
  const form = new FormData()
 | 
			
		||||
| 
						 | 
				
			
			@ -98,7 +98,7 @@ const updateAvatar = ({ credentials, params }) => {
 | 
			
		|||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const updateBg = ({ credentials, params }) => {
 | 
			
		||||
const updateBg = ({credentials, params}) => {
 | 
			
		||||
  let url = BG_UPDATE_URL
 | 
			
		||||
 | 
			
		||||
  const form = new FormData()
 | 
			
		||||
| 
						 | 
				
			
			@ -122,7 +122,7 @@ const updateBg = ({ credentials, params }) => {
 | 
			
		|||
// offset_left
 | 
			
		||||
// offset_top
 | 
			
		||||
// banner (base 64 encodend data url)
 | 
			
		||||
const updateBanner = ({ credentials, params }) => {
 | 
			
		||||
const updateBanner = ({credentials, params}) => {
 | 
			
		||||
  let url = BANNER_UPDATE_URL
 | 
			
		||||
 | 
			
		||||
  const form = new FormData()
 | 
			
		||||
| 
						 | 
				
			
			@ -145,7 +145,7 @@ const updateBanner = ({ credentials, params }) => {
 | 
			
		|||
// url
 | 
			
		||||
// location
 | 
			
		||||
// description
 | 
			
		||||
const updateProfile = ({ credentials, params }) => {
 | 
			
		||||
const updateProfile = ({credentials, params}) => {
 | 
			
		||||
  // Always include these fields, because they might be empty or false
 | 
			
		||||
  const fields = ['description', 'locked', 'no_rich_text', 'hide_follows', 'hide_followers', 'show_role']
 | 
			
		||||
  let url = PROFILE_UPDATE_URL
 | 
			
		||||
| 
						 | 
				
			
			@ -201,7 +201,7 @@ const authHeaders = (accessToken) => {
 | 
			
		|||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const externalProfile = ({ profileUrl, credentials }) => {
 | 
			
		||||
const externalProfile = ({profileUrl, credentials}) => {
 | 
			
		||||
  let url = `${EXTERNAL_PROFILE_URL}?profileurl=${profileUrl}`
 | 
			
		||||
  return fetch(url, {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
| 
						 | 
				
			
			@ -209,7 +209,7 @@ const externalProfile = ({ profileUrl, credentials }) => {
 | 
			
		|||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const followUser = ({ id, credentials }) => {
 | 
			
		||||
const followUser = ({id, credentials}) => {
 | 
			
		||||
  let url = MASTODON_FOLLOW_URL(id)
 | 
			
		||||
  return fetch(url, {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
| 
						 | 
				
			
			@ -217,7 +217,7 @@ const followUser = ({ id, credentials }) => {
 | 
			
		|||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const unfollowUser = ({ id, credentials }) => {
 | 
			
		||||
const unfollowUser = ({id, credentials}) => {
 | 
			
		||||
  let url = MASTODON_UNFOLLOW_URL(id)
 | 
			
		||||
  return fetch(url, {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
| 
						 | 
				
			
			@ -225,21 +225,21 @@ const unfollowUser = ({ id, credentials }) => {
 | 
			
		|||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const blockUser = ({ id, credentials }) => {
 | 
			
		||||
const blockUser = ({id, credentials}) => {
 | 
			
		||||
  return fetch(MASTODON_BLOCK_USER_URL(id), {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
    method: 'POST'
 | 
			
		||||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const unblockUser = ({ id, credentials }) => {
 | 
			
		||||
const unblockUser = ({id, credentials}) => {
 | 
			
		||||
  return fetch(MASTODON_UNBLOCK_USER_URL(id), {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
    method: 'POST'
 | 
			
		||||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const approveUser = ({ id, credentials }) => {
 | 
			
		||||
const approveUser = ({id, credentials}) => {
 | 
			
		||||
  let url = `${APPROVE_USER_URL}?user_id=${id}`
 | 
			
		||||
  return fetch(url, {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
| 
						 | 
				
			
			@ -247,7 +247,7 @@ const approveUser = ({ id, credentials }) => {
 | 
			
		|||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const denyUser = ({ id, credentials }) => {
 | 
			
		||||
const denyUser = ({id, credentials}) => {
 | 
			
		||||
  let url = `${DENY_USER_URL}?user_id=${id}`
 | 
			
		||||
  return fetch(url, {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
| 
						 | 
				
			
			@ -255,13 +255,13 @@ const denyUser = ({ id, credentials }) => {
 | 
			
		|||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchUser = ({ id, credentials }) => {
 | 
			
		||||
const fetchUser = ({id, credentials}) => {
 | 
			
		||||
  let url = `${MASTODON_USER_URL}/${id}`
 | 
			
		||||
  return promisedRequest(url, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((data) => parseUser(data))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchUserRelationship = ({ id, credentials }) => {
 | 
			
		||||
const fetchUserRelationship = ({id, credentials}) => {
 | 
			
		||||
  let url = `${MASTODON_USER_RELATIONSHIPS_URL}/?id=${id}`
 | 
			
		||||
  return fetch(url, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((response) => {
 | 
			
		||||
| 
						 | 
				
			
			@ -275,7 +275,7 @@ const fetchUserRelationship = ({ id, credentials }) => {
 | 
			
		|||
    })
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchFriends = ({ id, maxId, sinceId, limit = 20, credentials }) => {
 | 
			
		||||
const fetchFriends = ({id, maxId, sinceId, limit = 20, credentials}) => {
 | 
			
		||||
  let url = MASTODON_FOLLOWING_URL(id)
 | 
			
		||||
  const args = [
 | 
			
		||||
    maxId && `max_id=${maxId}`,
 | 
			
		||||
| 
						 | 
				
			
			@ -289,14 +289,14 @@ const fetchFriends = ({ id, maxId, sinceId, limit = 20, credentials }) => {
 | 
			
		|||
    .then((data) => data.map(parseUser))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const exportFriends = ({ id, credentials }) => {
 | 
			
		||||
const exportFriends = ({id, credentials}) => {
 | 
			
		||||
  let url = MASTODON_FOLLOWING_URL(id) + `?all=true`
 | 
			
		||||
  return fetch(url, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((data) => data.json())
 | 
			
		||||
    .then((data) => data.map(parseUser))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchFollowers = ({ id, maxId, sinceId, limit = 20, credentials }) => {
 | 
			
		||||
const fetchFollowers = ({id, maxId, sinceId, limit = 20, credentials}) => {
 | 
			
		||||
  let url = MASTODON_FOLLOWERS_URL(id)
 | 
			
		||||
  const args = [
 | 
			
		||||
    maxId && `max_id=${maxId}`,
 | 
			
		||||
| 
						 | 
				
			
			@ -310,20 +310,20 @@ const fetchFollowers = ({ id, maxId, sinceId, limit = 20, credentials }) => {
 | 
			
		|||
    .then((data) => data.map(parseUser))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchAllFollowing = ({ username, credentials }) => {
 | 
			
		||||
const fetchAllFollowing = ({username, credentials}) => {
 | 
			
		||||
  const url = `${ALL_FOLLOWING_URL}/${username}.json`
 | 
			
		||||
  return fetch(url, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((data) => data.json())
 | 
			
		||||
    .then((data) => data.map(parseUser))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchFollowRequests = ({ credentials }) => {
 | 
			
		||||
const fetchFollowRequests = ({credentials}) => {
 | 
			
		||||
  const url = FOLLOW_REQUESTS_URL
 | 
			
		||||
  return fetch(url, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchConversation = ({ id, credentials }) => {
 | 
			
		||||
const fetchConversation = ({id, credentials}) => {
 | 
			
		||||
  let urlContext = MASTODON_STATUS_CONTEXT_URL(id)
 | 
			
		||||
  return fetch(urlContext, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((data) => {
 | 
			
		||||
| 
						 | 
				
			
			@ -333,13 +333,13 @@ const fetchConversation = ({ id, credentials }) => {
 | 
			
		|||
      throw new Error('Error fetching timeline', data)
 | 
			
		||||
    })
 | 
			
		||||
    .then((data) => data.json())
 | 
			
		||||
    .then(({ ancestors, descendants }) => ({
 | 
			
		||||
    .then(({ancestors, descendants}) => ({
 | 
			
		||||
      ancestors: ancestors.map(parseStatus),
 | 
			
		||||
      descendants: descendants.map(parseStatus)
 | 
			
		||||
    }))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchStatus = ({ id, credentials }) => {
 | 
			
		||||
const fetchStatus = ({id, credentials}) => {
 | 
			
		||||
  let url = MASTODON_STATUS_URL(id)
 | 
			
		||||
  return fetch(url, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((data) => {
 | 
			
		||||
| 
						 | 
				
			
			@ -352,7 +352,7 @@ const fetchStatus = ({ id, credentials }) => {
 | 
			
		|||
    .then((data) => parseStatus(data))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchTimeline = ({ timeline, credentials, since = false, until = false, userId = false, tag = false, withMuted = false }) => {
 | 
			
		||||
const fetchTimeline = ({timeline, credentials, since = false, until = false, userId = false, tag = false, withMuted = false}) => {
 | 
			
		||||
  const timelineUrls = {
 | 
			
		||||
    public: MASTODON_PUBLIC_TIMELINE,
 | 
			
		||||
    friends: MASTODON_USER_HOME_TIMELINE_URL,
 | 
			
		||||
| 
						 | 
				
			
			@ -487,7 +487,7 @@ const unretweet = ({ id, credentials }) => {
 | 
			
		|||
    .then((data) => parseStatus(data))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const postStatus = ({ credentials, status, spoilerText, visibility, sensitive, mediaIds = [], inReplyToStatusId, contentType }) => {
 | 
			
		||||
const postStatus = ({credentials, status, spoilerText, visibility, sensitive, mediaIds = [], inReplyToStatusId, contentType}) => {
 | 
			
		||||
  const form = new FormData()
 | 
			
		||||
 | 
			
		||||
  form.append('status', status)
 | 
			
		||||
| 
						 | 
				
			
			@ -527,7 +527,7 @@ const deleteStatus = ({ id, credentials }) => {
 | 
			
		|||
  })
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const uploadMedia = ({ formData, credentials }) => {
 | 
			
		||||
const uploadMedia = ({formData, credentials}) => {
 | 
			
		||||
  return fetch(MASTODON_MEDIA_UPLOAD_URL, {
 | 
			
		||||
    body: formData,
 | 
			
		||||
    method: 'POST',
 | 
			
		||||
| 
						 | 
				
			
			@ -537,7 +537,7 @@ const uploadMedia = ({ formData, credentials }) => {
 | 
			
		|||
    .then((data) => parseAttachment(data))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const followImport = ({ params, credentials }) => {
 | 
			
		||||
const followImport = ({params, credentials}) => {
 | 
			
		||||
  return fetch(FOLLOW_IMPORT_URL, {
 | 
			
		||||
    body: params,
 | 
			
		||||
    method: 'POST',
 | 
			
		||||
| 
						 | 
				
			
			@ -546,7 +546,7 @@ const followImport = ({ params, credentials }) => {
 | 
			
		|||
    .then((response) => response.ok)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const deleteAccount = ({ credentials, password }) => {
 | 
			
		||||
const deleteAccount = ({credentials, password}) => {
 | 
			
		||||
  const form = new FormData()
 | 
			
		||||
 | 
			
		||||
  form.append('password', password)
 | 
			
		||||
| 
						 | 
				
			
			@ -559,7 +559,7 @@ const deleteAccount = ({ credentials, password }) => {
 | 
			
		|||
    .then((response) => response.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const changePassword = ({ credentials, password, newPassword, newPasswordConfirmation }) => {
 | 
			
		||||
const changePassword = ({credentials, password, newPassword, newPasswordConfirmation}) => {
 | 
			
		||||
  const form = new FormData()
 | 
			
		||||
 | 
			
		||||
  form.append('password', password)
 | 
			
		||||
| 
						 | 
				
			
			@ -574,31 +574,31 @@ const changePassword = ({ credentials, password, newPassword, newPasswordConfirm
 | 
			
		|||
    .then((response) => response.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchMutes = ({ credentials }) => {
 | 
			
		||||
const fetchMutes = ({credentials}) => {
 | 
			
		||||
  return promisedRequest(MASTODON_USER_MUTES_URL, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((users) => users.map(parseUser))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const muteUser = ({ id, credentials }) => {
 | 
			
		||||
const muteUser = ({id, credentials}) => {
 | 
			
		||||
  return promisedRequest(MASTODON_MUTE_USER_URL(id), {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
    method: 'POST'
 | 
			
		||||
  })
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const unmuteUser = ({ id, credentials }) => {
 | 
			
		||||
const unmuteUser = ({id, credentials}) => {
 | 
			
		||||
  return promisedRequest(MASTODON_UNMUTE_USER_URL(id), {
 | 
			
		||||
    headers: authHeaders(credentials),
 | 
			
		||||
    method: 'POST'
 | 
			
		||||
  })
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchBlocks = ({ credentials }) => {
 | 
			
		||||
const fetchBlocks = ({credentials}) => {
 | 
			
		||||
  return promisedRequest(MASTODON_USER_BLOCKS_URL, { headers: authHeaders(credentials) })
 | 
			
		||||
    .then((users) => users.map(parseUser))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const fetchOAuthTokens = ({ credentials }) => {
 | 
			
		||||
const fetchOAuthTokens = ({credentials}) => {
 | 
			
		||||
  const url = '/api/oauth_tokens.json'
 | 
			
		||||
 | 
			
		||||
  return fetch(url, {
 | 
			
		||||
| 
						 | 
				
			
			@ -611,7 +611,7 @@ const fetchOAuthTokens = ({ credentials }) => {
 | 
			
		|||
  })
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const revokeOAuthToken = ({ id, credentials }) => {
 | 
			
		||||
const revokeOAuthToken = ({id, credentials}) => {
 | 
			
		||||
  const url = `/api/oauth_tokens/${id}`
 | 
			
		||||
 | 
			
		||||
  return fetch(url, {
 | 
			
		||||
| 
						 | 
				
			
			@ -620,13 +620,13 @@ const revokeOAuthToken = ({ id, credentials }) => {
 | 
			
		|||
  })
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const suggestions = ({ credentials }) => {
 | 
			
		||||
const suggestions = ({credentials}) => {
 | 
			
		||||
  return fetch(SUGGESTIONS_URL, {
 | 
			
		||||
    headers: authHeaders(credentials)
 | 
			
		||||
  }).then((data) => data.json())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const markNotificationsAsSeen = ({ id, credentials }) => {
 | 
			
		||||
const markNotificationsAsSeen = ({id, credentials}) => {
 | 
			
		||||
  const body = new FormData()
 | 
			
		||||
 | 
			
		||||
  body.append('latest_id', id)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
Some files were not shown because too many files have changed in this diff Show more
		Loading…
	
		Reference in a new issue