aboutsummaryrefslogtreecommitdiff
path: root/resources/vue/components/blubber/ThreadsWidget.vue
blob: 72b1bf1a6493bc3c778a21a0dc3cc6ca023f29d6 (plain)
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
104
105
106
107
108
109
110
111
<template>
    <SidebarWidget :title="$gettext('Konversationen')" @scroll="handleScroll">
        <template #content>
            <div class="scrollable_area blubber_thread_widget" :class="{ scrolled }" ref="scrollableArea">
                <ol>
                    <li
                        v-for="thread in sortedThreads"
                        :key="thread.id"
                        :data-thread_id="thread.id"
                        :class="threadClasses(thread)"
                        :data-unseen_comments="thread.unseenComments"
                        @click.prevent="changeActiveThread(thread.id)"
                    >
                        <a :href="link(thread.id)">
                            <div class="avatar" :style="{ backgroundImage: 'url(' + thread.avatar + ')' }"></div>
                            <div class="info">
                                <div class="title">
                                    <span class="thread-name">{{ thread.name }}</span>
                                    <span v-if="thread.unseenComments > 0" class="unseen-comments-counter">{{ thread.unseenComments }}</span>
                                </div>
                                <studip-date-time
                                    :timestamp="threadLatestActivity(thread)"
                                    :relative="true"
                                ></studip-date-time>
                            </div>
                        </a>
                    </li>
                    <li class="more" v-if="hasMoreThreads" key="more" ref="more">
                        <studip-asset-img file="loading-indicator.svg" width="20"></studip-asset-img>
                    </li>
                </ol>
            </div>
        </template>

        <template #actions>
            <a :href="urlCompose" data-dialog="width=600;height=300">
                <studip-icon shape="add" />
            </a>
        </template>
    </SidebarWidget>
</template>
<script>
import SidebarWidget from '../SidebarWidget.vue';

export default {
    emits: ['load-more-threads', 'select-thread'],
    props: {
        hasMoreThreads: {
            type: Boolean,
            default: false,
        },
        threadId: {
            type: String,
            default: null,
        },
        threads: {
            type: Array,
            default: () => [],
        },
    },
    data: () => ({
        scrolled: false,
    }),
    components: {
        SidebarWidget,
    },
    computed: {
        sortedThreads() {
            const sorted = [...this.threads].sort((a, b) => {
                return (
                    new Date(b['latest-activity']) - new Date(a['latest-activity'])
                    || new Date(b['mkdate']) - new Date(a['mkdate'])
                    || b.name.localeCompare(a.name)
                );
            });

            return sorted;
        },
        urlCompose() {
            return STUDIP.URLHelper.getURL('dispatch.php/blubber/compose');
        },
    },
    methods: {
        changeActiveThread(threadId) {
            this.$emit('select-thread', threadId);
        },
        handleScroll({ element }) {
            this.scrolled = element.scrollTop > 0;

            if (
                this.hasMoreThreads
                && element.scrollTop >= element.scrollHeight - this.$refs.more.clientHeight - element.clientHeight
            ) {
                this.$emit('load-more-threads');
            }
        },
        link(thread_id) {
            return STUDIP.URLHelper.getURL(`dispatch.php/blubber/index/${thread_id}`);
        },
        threadClasses(thread) {
            return {
                active: thread.id === this.threadId,
                unseen: thread.unseenComments > 0,
            };
        },
        threadLatestActivity(thread) {
            return new Date(thread['latest-activity']) / 1000;
        },
    },
};
</script>