【问题标题】:How to pass updated data to already child vue component rendered如何将更新的数据传递给已经渲染的子 vue 组件
【发布时间】:2019-07-15 12:48:23
【问题描述】:

我正在尝试将一些 vars 更新到父组件中。我的情况是这样的:

我有一个父组件:

    import LugarListComponent from './LugarListComponent';
    import LugarAddComponent from './LugarAddComponent'

    export default {
        components:{
            'lugar-list-component' : LugarListComponent,
            'lugar-add-component' : LugarAddComponent,
        },
        data(){
            return {
                show: false,
                nombre: '',
                desc : '',
            }
        },
        methods:{
            showComponent: function () {
                this.show = true;
            },
            hideComponent: function () {
                this.show = false;
            },
            setLugar: function(lugar){
                this.show = true;
            }
        },
        mounted() {
            //console.log('Component mounted.')
        }
    }
<template>
    <div class="container">
        <h3>Lugares</h3>

        <div style="text-align: right">
            <button type="button" class="btn btn-primary" v-show="!show" v-on:click.prevent="showComponent"><i class="fa fa-plus"></i> Adicionar</button>
            <button type="button" class="btn btn-success" v-show="show" v-on:click.prevent="hideComponent"><i class="fa fa-arrow-left"></i> Regresar</button>
        </div>
        <br>

        <lugar-list-component v-show="!show" @setLugar="setLugar"></lugar-list-component>
        <lugar-add-component v-show="show" @hideComponent="hideComponent"></lugar-add-component>
    </div>
</template>

该组件有两个子组件,用于列出地点的 lugar-list 和用于添加地点的 lugar-add。当我显示其中一个时,我有一个用于控制的 show var。

我想编辑一个地方,但我想将数据发送到 lugar-add 以将他的值显示到此组件中,但我没有找到任何解决方案将变量更新为 lugar-add。这里我展示了这个组件的代码。

对于 lugar-add

export default {
        data(){
            return {
                image: '',
                nombre: '',
                desc : ''
            }
        },
        methods: {
            onImageChange(e) {
                let files = e.target.files || e.dataTransfer.files;
                if (!files.length)
                    return;
                this.createImage(files[0]);
            },
            createImage(file) {
                let reader = new FileReader();
                let vm = this;
                reader.onload = (e) => {
                    vm.image = e.target.result;
                };
                reader.readAsDataURL(file);
            },
            uploadImage(){
                axios.post('/lugar',{
                    image: this.image,
                    nombre: this.nombre,
                    desc: this.desc
                }).then(response => {
                    if(response.status == 200){
                        this.$emit('hideComponent')
                    }
                });
            },
            setAttributes(lugarEdit){
                console.log('disparado');
                this.nombre = lugarEdit.nombre;
                this.desc = lugarEdit.desc;
            }
        },
        mounted() {
            //console.log('Component mounted.');
            this.$on(
                'setAttributes',
                function(lugar) {
                    this.nombre = lugar.nombre;
                    this.desc = lugar.desc;
                }
            );
        }
<template>
    <div class="container">
        <div class="form-group">
            <label>Nombre</label>
            <input type="text" v-model="nombre" class="form-control" placeholder="Nombre del lugar">
        </div>

        <div class="form-group">
            <label for="descTexArea">Descripci&oacute;n</label>
            <textarea v-model="desc" class="form-control" id="descTexArea" rows="3"></textarea>
        </div>

        <div class="form-group">
            <label for="exampleFormControlFile1">Subir im&aacute;genes</label>
            <input type="file" v-on:change="onImageChange" class="form-control-file" id="exampleFormControlFile1">
        </div>

        <div class="form-group">
            <button type="button" class="btn btn-primary" @click="uploadImage">Adicionar</button>
        </div>


        <div class="col-md-3" v-if="image">
            <img :src="image" class="img-responsive" height="70" width="90">
        </div>
    </div>
</template>

这里我使用事件来隐藏这个组件并显示 lugar-list 组件。这是 lugar-list 的代码

export default {
        name: 'lugar-list-component',
        data:function(){
            return {
                listLugares : [],
                id : '',
            }
        },
        methods:{
            getLugares: function () {
                fetch('/lugar')
                    .then(response => response.json())
                    .then(res => {
                        this.listLugares = res;
                    })
            },
            setId: function(id){
                this.id = id;
            },
            removeLugar: function(id){
                this.id = id;
                axios.delete('lugar/'+id)
                    .then(response => {
                        this.getLugares();
                    });
            },
            editLugar: function(id){
                this.id = id;

                axios.get('lugar/'+id)
                    .then(response => {
                        this.$emit('setLugar',response);
                    });
            },
        },
        mounted() {
            this.getLugares();
        }
    }
<template>
    <div class="container">

        <table class="table table-striped">
            <thead>
            <tr>
                <th scope="col">#</th>
                <th scope="col">Nombre</th>
                <th scope="col">Desc.</th>
                <th scope="col">Fecha</th>
                <th scope="col">Acciones</th>
            </tr>
            </thead>
            <tbody>
            <tr v-for="(item, index) in listLugares">
                <th scope="row">{{ index+1 }}</th>
                <td>{{ item.nombre }}</td>
                <td>{{ item.desc }}</td>
                <td>{{ item.created_at }}</td>
                <td>
                    <button type="button" class="btn btn-success" v-on:click.prevent="editLugar(item.id)"><i class="fa fa-edit"></i> Editar</button>
                    <button type="button" class="btn btn-danger" v-on:click.prevent="removeLugar(item.id)"><i class="fa fa-remove"></i> Eliminar</button>
                </td>
            </tr>

            </tbody>
        </table>


    </div>
</template>

希望你能理解我。谢谢。

【问题讨论】:

    标签: laravel vue.js components


    【解决方案1】:

    我没有找到其他使用带参数的路由的解决方案,我相信这是最好的解决方案。

    这是我的路线

    {
            path: '/lugar', component: require('./components/lugar/LugarComponent').default,
            children: [
                { path: '', component: LugarList },
                {
                    path: 'add/:id?',
                    name: 'lugarAdd',
                    component: LugarAdd
                },
                {
                    path: 'list',
                    component: LugarList
                }
            ]
        }

    添加地点的路线有一个可选参数。

    现在,在 Add 组件中,我使用以下代码获取参数:

    this.id = this.$route.params.id;
                    this.modeEdit = true;
    
                    axios.get('/lugar/'+this.id)
                        .then(response => {
                            this.nombre = response.data.nombre;
                            this.desc = response.data.desc;
    
                            for(let i = 0; i<response.data.images.length; i++){
                                this.image.push(response.data.images[i]);
                            }
                        });

    当我获得地点 ID 时,我会通过 axios 请求其信息。

    【讨论】:

      【解决方案2】:

      从第一个子组件发出一个事件来更新父组件。然后将要更新的值作为道具传递给第二个子元素。

      【讨论】:

      • 我对此进行了测试。问题是我认为该组件确实被渲染了,我在 lugar-list 组件中有一个事件,用于通知父组件我要编辑的位置,“editLugar”。这个函数触发了父级的setLugar函数,这里我得到了位置,但我不知道如何发送这个新数据来添加组件。
      • 我不确定你的意思。您只是想在子组件上触发一个动作,或者向它添加一些数据?如果你想添加一些数据,那么你应该将父组件中的所有数据都放在一个数据中。然后在从第一个孩子接收数据时,附加/更新父母的数据。然后,您将数据(始终是最新的)从父级传递给第二个子级作为道具。对 prop 的更改将自动反映在子组件中。
      猜你喜欢
      • 2017-11-09
      • 1970-01-01
      • 2021-04-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-04-15
      • 2018-11-12
      • 1970-01-01
      相关资源
      最近更新 更多