Laravel livewire and vuejs infinite scroll

Viewed 420

I have a livewire filter component which I want to filter results by

  1. All
  2. Popular
  3. Latest etc...

This in turn loads the vuejs infinite scroll.

When the page loads, the default filter which is "all", fetches the records and it displays the results fine. When another option is selected e.g. latest, I would like to reload the vuejs infinite scroll and load the latest data, but I get blank results and I can't reload it.

My filter form

<div>
    <button wire:click.prevent="all">Show All</button>
</div>
<div>
    <button wire:click.prevent="latest">Latest</button>
</div>
<div>
    <button wire:click.prevent="popular">Popular</button>
</div>

I emit an event in livewire to the component that loads the vuejs infinite scroll

public $categories;
public $tags;
public $searchType = 'all';
public $keyword;

public function all()
{
    $this->emit('all', 'all');
}

public function latest()
{
    $this->emit('latest', 'latest');
}

public function popular()
{
    $this->emit('popular', 'popular');
}

Calling the listener in other component

public function all()
{
    $this->searchType = 'all';
}

public function popular()
{
    $this->searchType = 'popular';
}

public function latest()
{
    $this->searchType = 'popular';
}

My component with the infinite scroll

<div>
    @livewire('search', [
        'searchType' => $searchType
    ])

    <post-view inline-template>
        <groups-infinite-scroll
            searchtype="{{$searchType}}"></groups-infinite-scroll>
    </post-view>

</div>

Is there a way to reload the vuejs compionent without reloading the page

Thanks in advance Danny

1 Answers

You need to change the way you are setting the searchType variable. Follow These steps:

For updating the searchType variable you need only one function to be called. That is a magic function from livewire. $set magic action.

    $set('variableName',value)

You don't need any controller code to change a variable value;

<div>
    <button wire:click="$set('searchType','all')">Show All</button>
</div>
<div>
    <button wire:click="$set('searchType','latest')">Latest</button>
</div>
<div>
    <button wire:click="$set('searchType','popular')">Popular</button>
</div>

As I said this won't need any controller code to change props value.


If you are still wondering why your previous code is not working because of you are not listening to the event you have fired.

Set you listener property using getListeners method.

    public function getListeners(){
        return ['all','latest','popular'];
    }

Whenever you fire an event named all or latest or popular it will call a method of that event name. This will definately work.

But You can still do it in smaller way. The best workaround is given below.

1.From blade fire only one method except three .

<div>
    <button wire:click="setSearchType('all')">Show All</button>
</div>
<div>
    <button wire:click="setSearchType('latest')">Latest</button>
</div>
<div>
    <button wire:click="setSearchType('popular')">Popular</button>
</div>
  1. create a setSearchType method on the controller.

    public function setSearchType($value) { $this->searchType = $value; }

That's all. You don't need fire and event to update the value.


If you still want to set property value using the event. Just like previously create a listener for just one event ('setSearchTypePropery'); Then update the search type variable there.

public function getListeners(){
    return ['setSearchTypePropery'];
}
public function setSearchType($value)
{
    $this->emit('setSearchTypePropery'.['value'=>$value]);
}

public function setSearchTypePropery($param){
    $this->searchType = $param['value'];
}

That is all. Have a good day.

Related