1.web即时通讯

https://cloud.tencent.com/document/product/269/75319(文档)

https://web.sdk.qcloud.com/im/doc/zh-cn/TIM.html(API)

2.main中引入

// 从v2.11.2起,SDK 支持了 WebSocket,推荐接入;v2.10.2及以下版本,使用 HTTP
// v2.24.0起,SDK 支持使用本地审核插件
import TIM from 'tim-js-sdk';
import TIMUploadPlugin from 'tim-upload-plugin';
import TIMProfanityFilterPlugin from 'tim-profanity-filter-plugin';

let options = {
  SDKAppID: 1400793822 // 接入时需要将0替换为您的即时通信 IM 应用的 SDKAppID
};
// 创建 SDK 实例,`TIM.create()`方法对于同一个 `SDKAppID` 只会返回同一份实例
let tim = TIM.create(options); // SDK 实例通常用 tim 表示

// 设置 SDK 日志输出级别,详细分级请参见 setLogLevel https://web.sdk.qcloud.com/im/doc/zh-cn/SDK.html#setLogLevel 接口的说明</a>
tim.setLogLevel(0); // 普通级别,日志量较多,接入时建议使用
// tim.setLogLevel(1); // release 级别,SDK 输出关键信息,生产环境时建议使用

// 注册腾讯云即时通信 IM 上传插件
tim.registerPlugin({'tim-upload-plugin': TIMUploadPlugin});

// 注册腾讯云即时通信 IM 本地审核插件
tim.registerPlugin({'tim-profanity-filter-plugin': TIMProfanityFilterPlugin});

Vue.prototype.TIM = TIM
Vue.prototype.tim = tim

3.引入下载好debug

4.在需要的页面

import { genTestUserSig } from '@/debug/GenerateTestUserSig'

首先要登录  
login(){
    let userSig=genTestUserSig(this.userName).userSig
    let promise = this.tim.login({userID: this.userName, userSig: userSig});
    promise.then(function(imResponse) {
    console.log(imResponse.data); // 登录成功
    if (imResponse.data.repeatLogin === true) {
        // 标识帐号已登录,本次登录操作为重复登录。v2.5.1 起支持
        console.log(imResponse.data.errorInfo);
        
    }
    }).catch(function(imError) {
    console.warn('login error:', imError);
    });
},

登录成功后需要加入群组

joinGrop(){
    let promise = this.tim.joinGroup({ groupID: '10012345' });
    promise.then(function(imResponse) {
    console.log(imResponse.data.status) 
    switch (imResponse.data.status) {
        case this.TIM.TYPES.JOIN_STATUS_WAIT_APPROVAL: // 等待管理员同意
        break;
        case this.TIM.TYPES.JOIN_STATUS_SUCCESS: // 加群成功
        console.log(imResponse.data.group); // 加入的群组资料
        break;
        case this.TIM.TYPES.JOIN_STATUS_ALREADY_IN_GROUP: // 已经在群中
        break;
        default:
        break;
    }
    }).catch(function(imError){
    console.warn('joinGroup error:', imError); // 申请加群失败的相关信息
    });
},

发送文字

sendMessage(){
    let message = this.tim.createTextMessage({
        to: '10012345',
        conversationType: this.TIM.TYPES.CONV_GROUP,
        payload: {
            text: this.message
        },
        needReadReceipt: true
    });
    let promise = this.tim.sendMessage(message);
    let _this=this
    promise.then(function(imResponse) {
        _this.message=''
       _this.msglist=[..._this.msglist,...[imResponse.data.message]]
    }).catch(function(imError) {});
},

然后就是监听

 mounted() {
    let onMessageReceived = function(event) {
        this.msglist=[...this.msglist,...event.data]
    };
    this.tim.on(this.TIM.EVENT.MESSAGE_RECEIVED, onMessageReceived,this);
},
<template>
    <div class="detail">
        <div class="box_title">
            <div class="box_title_left">
                {{ name }}
            </div>
            <div class="box_title_right">
                <div class="title">
                    <span class="el-icon-location-outline" style="color:#E23430"></span> 当前位置:  
                    <router-link :to="path"><span style="color:#333333" @click="handleClick()">首页</span> </router-link> /  {{ name }} 
                </div>
               <img src="@/assets/static/news/back.png" @click="handleBack()" />
            </div>
        </div>
        <div class="content_box">
               <div class="studyInfo_box">
                   <div class="title">{{DetailInfo.title}}</div>
               </div>
               <div class="video_box">
                    <div class="left">
                       <video id="videoElement" class="study_video" src="http://zb.dangjian.link/live/3935.flv" controls  autoplay></video>
                    </div>
                   <div class="right">
                       <div class="user_box">
                        <div class="tab_item" v-for="(item, index) in tabList" :key="index" 
                            :class="TabCur == index ? 'activeItem' : '' " @click="TabClick(item, index)">
                            {{ item }}
                        </div>
                       </div>
                       <div class="mulu_box" v-if="TabCur==1">
                            <div class="top">
                                <div class="avatar">
                                    <img src="../../assets/static/index/tu3.png">
                                </div>
                                <div class="username">主讲人: {{ DetailInfo.assistanName }}</div>
                            </div>
                            <div class="desc" v-html="DetailInfo.content"></div>
                       </div>
                       <div class="pinglun_box" v-if="TabCur==0">
                           <div class="danmu" ref="QAContent">
                                <div class="initmessage">
                                    欢迎来到直播间!直播间内严禁出现违法违规、低俗色情、吸烟、熏酒、人身伤害等内容。请大家注意财产安全
                                    ,谨防网络诈骗!
                                </div>
                                <div class="pinglun_item" v-for="(item,index) in msglist" :key="index">
                                    <i class="el-icon-s-custom" style="color: #a5a5a5;"></i>
                                    <span class="name">{{item.from}}:</span>
                                    <span class="count">{{item.payload.text}}</span>
                                </div>
                           </div>
                           <div style="margin-top: 15px;">
                                <el-input placeholder="请输入内容" v-model="message" class="input-with-select" @keyup.enter.native="keyDown">
                                    <el-button slot="append" type="danger" style="background-color: #e40b0b;color: #fff;" @click="sendMessage">发 送</el-button>
                                </el-input>
                            </div>
                       </div>
                   </div>
               </div>

        </div>

    </div>
</template>

<script>
    import { mapGetters } from "vuex"
    import { genTestUserSig } from '@/debug/GenerateTestUserSig'
    import flvjs from "flv.js"
    export default {
        data() {
            return {
                name: "直播",
                TabCur: 0, 
                tabList: ["直播间互动", "直播间简介"],
                DetailInfo:{}, 
                message:'',
                flvPlayer: null,
                msglist:[], 
            }
        },
        computed: {
            ...mapGetters(['token','userName']),
            path(){
                return localStorage.getItem("manageActive") 
            },
            playId () {
                return Number( this.$route.params.id)
            },
        },
        created() {
            this.login()
        },
        mounted() {
            this.getplayInit()
            this.Grop()
            let onMessageReceived = function(event) {
                this.msglist=[...this.msglist,...event.data]
                this.scrollToBottom()
            };
            this.tim.on(this.TIM.EVENT.MESSAGE_RECEIVED, onMessageReceived,this);
        },
        methods: {
            login(){
                let userSig=genTestUserSig(this.userName).userSig
                let promise = this.tim.login({userID: this.userName, userSig: userSig});
                promise.then(function(imResponse) {
                    if (imResponse.data.repeatLogin === true) {
                        console.log(imResponse.data.errorInfo);
                    }
                })
            },
            Grop(){
                let promise = this.tim.joinGroup({ groupID: '10012345' });
                promise.then(function(imResponse) {
                    switch (imResponse.data.status) {
                        case this.TIM.TYPES.JOIN_STATUS_WAIT_APPROVAL: // 等待管理员同意
                        break;
                        case this.TIM.TYPES.JOIN_STATUS_SUCCESS: // 加群成功
                        console.log(imResponse.data.group); // 加入的群组资料
                        break;
                        case this.TIM.TYPES.JOIN_STATUS_ALREADY_IN_GROUP: // 已经在群中
                        break;
                        default:
                        break;
                    }
                })
            },
            sendMessage(){
                let message = this.tim.createTextMessage({
                    to: '10012345',
                    conversationType: this.TIM.TYPES.CONV_GROUP,
                    payload: {
                        text: this.message
                    },
                    needReadReceipt: true
                });
                let promise = this.tim.sendMessage(message);
                let _this=this
                promise.then(function(imResponse) {
                    _this.message=''
                   _this.msglist=[..._this.msglist,...[imResponse.data.message]]
                   _this.scrollToBottom()
                }).catch(function(imError) {});
            },
            scrollToBottom() {
                this.$nextTick(() => {
                    let scrollElem = this.$refs.QAContent;
                    console.log('scrollHeight: ', scrollElem.scrollHeight);
                    scrollElem.scrollTo({
                    top: scrollElem.scrollHeight,
                    behavior: 'smooth'
                    });
                });
            },
            TabClick ( item, index ) {
                this.TabCur = index
            },
            keyDown(e) {
                if(this.message) this.sendMessage();
            },
            handleClick(){
                localStorage.setItem("tabActive", 0)
                this.$store.commit("setabActive", 0 )
            },
            handleBack(){
                this.$router.go(-1)
            },
            async getplayInit() {
                let { token, playId } = this 
                let res = await this.$axios.post("/lencon/pc/zhiBo/zhiboDetail", { token, id:playId })
                if ( res.data.code == 1 ) {
                    this.DetailInfo=res.data
                    if( this.DetailInfo.llUrl) this.play()
                }
            },
            play(){
                var videoElement = document.getElementById('videoElement');
                this.flvPlayer = flvjs.createPlayer({
                    type: 'flv',
                    url: this.DetailInfo.llUrl
                });
                this.flvPlayer.attachMediaElement(videoElement);
                this.flvPlayer.load();
                this.flvPlayer.play();
            },
            scrollTop () {
                document.documentElement.scrollTop = 0
            },
        },
        beforeDestroy(){
            this.tim.destroy();
            if(this.flvPlayer){
                this.flvPlayer.pause();
                this.flvPlayer.unload();
                this.flvPlayer.detachMediaElement();
                this.flvPlayer.destroy();
                this.flvPlayer = null;
            }
        }
    }
</script>

<style lang="scss" scoped>
@import "../../assets/css/main.scss";


.detail {
    width: 1200px;
    min-height: 700px;
    margin: 20px auto;
    .box_title {
        color: #E23430;
        display: flex;
        align-items: center;
        justify-content: space-between;
        padding-left: 20px;
        border-left: 4px solid #E23430;
        margin: 20px 0;
        .box_title_left {
            font-size: 24px;
            font-weight: bold;
        }
        .box_title_right {
            font-size: 16px;
            color: #333333;
            font-family: Microsoft YaHei;
            font-weight: 400;
            display: flex;
            align-items: center;
            img{
                width: 70px;
                margin-left: 10px;
                cursor: pointer;
            }
        }
    }
    .content_box {
        width: 1200px;
        padding: 40px;
        background-color: #fff;
        position: relative;
        left: 0;
        top: 0;
        .fixed_box {
            position: fixed;
            box-shadow: 0 0 10px 2px #eee;
            top: 370px;
            left: 200px;
            background-color: #fff;
            width: 100px;
            border-radius: 5px;
            // border: 1px solid #EDEDED;
            overflow: hidden;
            .item {
                padding: 20px 10px;
                text-align: center;
                cursor: pointer;
                .red {
                    color: #d30000;
                    
                }
                .gray {
                    color: #b3b3b3 ;
                }
            }
            .active {
                background-color: #d30000;
                color: #ffffff !important;
                .icon {
                    color: #fff;
                }
            }
        }
        .studyInfo_box {
            width: 100%;
           .title {
               width: 100%;
               font-size: 24px;
               line-height: 60px;
               text-align: left;
           }
           
        }
        .video_box {
               width: 100%;
               display: flex;
               .left{
                   width: 70%;
                   video {
                       width: 100%;
                       height: 440px;
                   }
               }
               .right {
                   width: 30%;
                   height: 440px;
                   background: rgb(74, 74, 74);
                   .user_box {
                       width: 100%;
                       display: flex;
                        .tab_item {
                            width: 50%;
                            text-align: center;
                            line-height: 40px;
                            cursor: pointer;
                            font-size: 16px;
                            background:#969696;
                            color:#dedede;
                        }
                        .activeItem {
                            background:#000000;
                            color: #ffffff;
                        }
                   }
                   .pinglun_box{
                       padding: 10px;
                       .danmu{
                             height: 330px;
                             font-size: 14px;
                             overflow-y: scroll;
                             &::-webkit-scrollbar {
                                display: none;
                            }
                            .initmessage{
                                color: #e6a23c;
                                margin-bottom: 10px;
                            }
                            .pinglun_item{
                                margin: 6px 0;
                                .name{
                                    color: #a5a5a5;
                                    margin: 0 8px 0 2px;
                                }
                                .count{
                                    color: #fff;
                                }
                        }
                       }
                       
                   }
                   .mulu_box {
                       width: 100%;
                       max-height: 300px;
                       overflow-y: scroll;
                       &::-webkit-scrollbar {
                           display: none;
                       }
                       .top {
                           width: 100%;
                           padding: 20px;
                           display: flex;
                           align-items: center;
                           .avatar {
                               width: 60px;
                               height: 60px;
                               border-radius: 50%;
                               overflow: hidden;
                               img {
                                   width: 60px;
                                   height: 60px;
                               }
                           }
                           .username {
                               color: #ffffff;
                               width: 50%;
                               margin-left: 20px;
                           }
                       }
                       .desc {
                           padding: 10px;
                           font-size: 14px;
                           color: #B9B8B8;
                           span {
                               overflow: hidden;
                               text-overflow: ellipsis;
                               white-space: nowrap;
                           }
                       }
                   }
               }
           }
        .biref {
            width: 100%;
            .b_title {
                width: 100%;
                color: #d30000;
                font-size: 24px;
                line-height: 60px;
                border-bottom: 1px solid #D91717;
                font-weight: bold;
            }
            .user {
                width: 100%;
                display: flex;
                align-items: center;
                padding: 20px;
                .left {
                    width: 60px;
                    height: 60px;
                    border-radius: 50%;
                    overflow: hidden;
                    img {
                        width: 60px;
                        height: 60px;
                    }
                }
                .right {
                    margin-left: 20px;
                    font-size: 16px;
                    .username {
                        line-height: 30px;
                    }
                }
            }
        }


        .bottom_box {
            width: 100%;
            margin-top: 50px;
            .tuijian_title {
                font-size: 24px;
                font-weight: bold;
                color: #d30000;
                padding-bottom: 10px;
                border-bottom: 1px solid #d30000;
            }
            .list_content {
                margin-top: 40px;
                width: 100%;
                display: flex;
                align-items: center;
                .list_item {
                    width: 270px;
                    margin-right: 10px;
                    cursor: pointer;
                    img {
                        width: 270px;
                        height: 160px;
                    }
                    .item_title {
                        font-size: 16px;
                        padding: 10px;
                    }
                    .item_bar {
                        display: flex;
                        justify-content: space-between;
                        align-items: center;
                        padding: 10px;
                        font-size: 14px;
                        color: #9B9B9B;
                    }
                }
            }
        }
    }

    
}
</style>

文件路径在下载中心

Logo

网易智企-云信开发者社区是面向全网开发者的技术交流与服务平台,依托近 29 年 IM、音视频技术积累,提供 IM、RTC、实时对话智能体、云原生、短信等全场景开发资源。

更多推荐