All files / app/assets/javascripts/diffs/components diff_gutter_avatars.vue

100% Statements 11/11
100% Branches 2/2
100% Functions 7/7
100% Lines 11/11

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103            9x                                             24x     24x           24x     24x 17x     7x         23x 23x 8x     23x                                                                                              
<script>
import { GlTooltipDirective, GlIcon } from '@gitlab/ui';
import { truncate } from '~/lib/utils/text_utility';
import { n__ } from '~/locale';
import UserAvatarImage from '~/vue_shared/components/user_avatar/user_avatar_image.vue';
import { COUNT_OF_AVATARS_IN_GUTTER, LENGTH_OF_AVATAR_TOOLTIP } from '../constants';
import { HIDE_COMMENTS } from '../i18n';
 
export default {
  components: {
    GlIcon,
    UserAvatarImage,
  },
  directives: {
    GlTooltip: GlTooltipDirective,
  },
  props: {
    discussions: {
      type: Array,
      required: true,
    },
    discussionsExpanded: {
      type: Boolean,
      required: false,
      default: false,
    },
  },
  computed: {
    allDiscussions() {
      return this.discussions.reduce((acc, note) => acc.concat(note.notes), []);
    },
    notesInGutter() {
      return this.allDiscussions.slice(0, COUNT_OF_AVATARS_IN_GUTTER).map((n) => ({
        note: n.note,
        author: n.author,
      }));
    },
    moreCount() {
      return this.allDiscussions.length - this.notesInGutter.length;
    },
    moreText() {
      if (this.moreCount === 0) {
        return '';
      }
 
      return n__('%d more comment', '%d more comments', this.moreCount);
    },
  },
  methods: {
    getTooltipText(noteData) {
      let { note } = noteData;
      if (note.length > LENGTH_OF_AVATAR_TOOLTIP) {
        note = truncate(note, LENGTH_OF_AVATAR_TOOLTIP);
      }
 
      return `${noteData.author.name}: ${note}`;
    },
  },
  i18n: {
    HIDE_COMMENTS,
  },
};
</script>
 
<template>
  <div class="diff-comment-avatar-holders">
    <button
      v-if="discussionsExpanded"
      v-gl-tooltip
      :title="$options.i18n.HIDE_COMMENTS"
      type="button"
      :aria-label="$options.i18n.HIDE_COMMENTS"
      class="diff-notes-collapse js-diff-comment-avatar js-diff-comment-button"
      @click="$emit('toggleLineDiscussions')"
    >
      <gl-icon :size="12" name="collapse" />
    </button>
    <template v-else>
      <user-avatar-image
        v-for="note in notesInGutter"
        :key="note.id"
        :img-src="note.author.avatar_url"
        :size="24"
        :tooltip-text="getTooltipText(note)"
        lazy
        class="diff-comment-avatar js-diff-comment-avatar"
        @click.native="$emit('toggleLineDiscussions')"
      />
      <span
        v-if="moreText"
        v-gl-tooltip
        :title="moreText"
        class="diff-comments-more-count js-diff-comment-avatar js-diff-comment-plus"
        data-container="body"
        data-placement="top"
        role="button"
        @click="$emit('toggleLineDiscussions')"
        >+{{ moreCount }}</span
      >
    </template>
  </div>
</template>