Vue2 消息订阅与发布

1.pubsub-js 第三方库实现

实现任何框架的消息订阅发布

npm i pubsub-js

<template>
  <div class="student">
    <h2>展示学生的名称:{{ name }}</h2>
    <h2>展示学生的性别:{{ sex }}</h2>
  </div>
</template>

<script>
import pubsub from "pubsub-js";

export default {
  name: "MyStudentt",
  data() {
    //这里存放数据
    return {
      name: "我是一个人",
      sex: 12,
    };
  },
  mounted() {
    // console.log(this.$refs.school1.__proto__===this.$refs.school2.__proto__);//true
    //   this.$bus.$on("show", (data)=>{
    //     console.log('事件总线收到了数据',data); 两个都生效
    //     this.name = data;
    //   });
    //  this.$bus.$on("show", (data)=>{
    //     console.log('事件总线收到了数据1',data);
    //     this.sex = data;
    //   });
    //订阅一个消息 show 是一个主题
   const pubId =  pubsub.subscribe("show", (msg, data) => {
      //消费者
      console.log("有人发布了消息,show消息回调成功", data);
      this.name = data;
    });

   this.pubId = pubId;
    //   pubsub.subscribe('show',(msg,data)=>{//消费者
    //   console.log('有人发布了消息,show消息回调成功',data);
    //   this.sex = data;
    // })
  },
  beforeDestroy() {
    // this.$bus.$off("show");

    pubsub.unsubscribe(this.pubId);
  },
};
</script>

<style scoped>
.student {
  background-color: green;
  padding: 5px;
  margin-top: 30px;
}
</style>
<template>
  <div class="school">
    <h2 >展示学校的名称:{{name}}</h2>
    <h2>展示学校的地址:{{ address }}</h2>
    <button @click="show">传入事件总线数据</button>
  </div>
</template>

<script>


import pubsub from 'pubsub-js';

export default {
  name: "MySchool",
  data() {
    //这里存放数据
    return {
      name: "辽工",
      address: "锦州",
    };
  },
  methods:{
      show(){
          // this.$bus.$emit('show',this.name);
          pubsub.publish('show',this.name);
      }




  }
  

};
</script>
<style scoped>

  .school{
    background-color: red;
    padding: 5px;
     margin-top: 30px;
  }

</style>
<template>
  <div class="app">
    <h1>{{ msg }}</h1>
    <Student ref="student"/>
    <MySchool ref="school"/>
  </div>
</template>

<script>
//引入School组件 随便起名字
import Student from "./components/Student.vue";
import MySchool from "./components/School.vue"; 

export default {
  name: "App",
  components: {
    Student,
    MySchool,
  },
  data() {
    return {
      msg: "你好啊!",
    };
  },
  mounted(){
  
  }
};
</script>

<style scoped>
.app {
  background-color: gray;
  padding: 5px;
}
</style>

2.$nextTick

<template>
  <div
    id="container"
    @mouseover="handleMouseOver"
    @mouseleave="handleMouseLeave"
  >
    <div id="d">
      <input type="checkbox" v-model="todo.done" />

      <span @click="info" v-show="!todo.showUpdate">{{ todo.title }}</span>
        
      <!-- v-inputfocus="todo.showUpdate" -->
      <input
        type="text"
        ref="updateInput"
        v-model="updateTitle"
        @keyup.enter="submitUpdate"
        @blur="cancelUpdate"
        v-show="todo.showUpdate"
      />
    </div>
    <div>
      <button class="btn update" v-show="showDelete" @click="updateTodo">
        修改
      </button>
      <button class="btn" v-show="showDelete" @click="deleteTodo">删除</button>
    </div>
  </div>
</template>

<script>
import pubsub from "pubsub-js";

export default {
  name: "TodoItem",
  data() {
    return {
      todo: this.todoObj,
      updateTitle: "",
      showDelete: false,
    };
  },
  methods: {

    //todo.hasOwnProperty这个属性是否有api  
    removeFocus() {
      //  this.$refs.updateInput.blur();
    },
    info() {
      console.log(this.todo);
    },
    handleMouseOver() {
      this.showDelete = true;
    },
    handleMouseLeave() {
      this.showDelete = false;
    },
    deleteTodo() {
      //  let a = this.$bus.$emit('removeTodo',this.todoObj.id)
      //  console.log(a===this.$bus);//a === vm

      if (confirm("你确定要删除吗?")) {
        pubsub.publish("removeTodo", this.todoObj.id);
      }
    },
    updateTodo() {
      if (this.todo.showUpdate) {
        this.todo.showUpdate = false;
      } else {
        this.updateTitle = this.todo.title;
        // this.$bus.$emit("updateTodoInputShow", this.todoObj.id, true);
        this.todo.showUpdate = true;
        //vue 提供api 在下次dom节点更新完毕后执行的回调
        this.$nextTick(function(){
          this.$refs.updateInput.focus();
          // console.log(this.$refs.updateInput);
        });

      }
      //vue 是等方法结束以后才回去解析模板, input框 focus 在display状态是不会聚焦的
    },

    submitUpdate() {
      if (confirm("你确定要保存吗?")) {
        if(this.updateTitle.trim()===''){
          alert('输入不能为空')
          return;
        }
        this.$bus.$emit("updateTodo", this.todo.id, this.updateTitle);
      }
      this.todo.showUpdate = false;
    },
    cancelUpdate() {
      this.todo.showUpdate = false;
    },
  },
  props: {
    todoObj: {
      //传入的若是引用对象 则里面修改了,外面同样生效
      type: Object,
      required: true,
    },
  },
  directives: {
    // inputfocus(e,v){
    //   if (v) {
    //       e.focus();
    //     }
    // }
    // inputfocus: {
    //   inserted(element, value) {
    //     if (value) {
    //       element.focus();
    //     }
    //   },
    //   update(element, value) {
    //     if (value) {
    //       element.focus();
    //     }
    //   },
    // },
  },
};
</script>

<style scoped>
#container:hover {
  background-color: #a09a9a;
}

#container {
  display: flex;
  justify-content: space-between; /*  水平居左 */
  align-items: center; /* 垂直居中 */
  width: 500px;
  height: 30px;
  border: 0.1px solid #ccc;
  border-radius: 2px;
  padding-left: 10px;
  padding-top: 5px;
  padding-bottom: 5px;
}

#container * {
  padding: 5px;
}

.btn {
  width: 50px;
  height: 28px;
  color: white;
  background-color: #eb1212;
  border: 1px solid #ccc;
  border-radius: 5px;
  padding: 5px;
  margin-right: 15px;
  cursor: pointer; /* 鼠标悬停时显示手型光标 */
  transition: background-color 0.3s ease; /* 平滑过渡 */
}
.btn:hover {
  background-color: #d10d0d; /* 鼠标悬停时颜色变化 */
}

.btn:active {
  background-color: #a00; /* 按下时颜色变化 */
  transform: translateY(2px); /* 按下时按钮下移效果 */
}

.update {
  background-color: #1233eb;
  margin-right: 5px;
}
.update:hover {
  background-color: #4e70dc; /* 鼠标悬停时颜色变化 */
}
.update:active {
  background-color: rgb(71, 0, 170); /* 按下时颜色变化 */
  transform: translateY(2px); /* 按下时按钮下移效果 */
}
</style>

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值