admin管理员组

文章数量:1289845

This is my first VueJS project (making the move from jQuery) and I am trying to filter a grid with multiple checkboxes. As you can see from the JavaScript, I have a filterJobs function that filters the array with values set from whats checked (the v-model="checkedLocations"). array.includes appears to filter on a single value and I'd like to filter multiple values. I don't want to pop or slice the array because if they uncheck a location the they'll be gone and won't rebind

let careers = careers || {};

 careers.taleo = (function($){

   let app;

   let init = function() {

    app = new Vue({
      el: '#app',
      data: {
        locations: ['Scottsdale, AZ','Chandler, AZ','Irvine, CA','Denver, CO','Chicago, IL','Rockville, MD','Kansas City, MO','Charlotte, NC','Red Bank, NJ','Henderson, NV','Melville, NY','Allentown, PA','Irving, TX'],
        jobs: null,
        checkedLocations: []
      },
      created: function () {
        this.fetchData();
      },
      methods: {
          fetchData: function () {
            this.jobs = [
              { id: '1', title: 'Circuit Court Clerk', description: 'lorem ipsum', location: 'Charlotte, NC', department: 'Sales and Marketing', date: '23/10/17' },
              { id: '2', title: 'Tie Buyer', description: 'lorem ipsum', location: 'Irvine, CA', department: 'Media Relations', date: '21/10/16' },
              { id: '3', title: 'Leaded Glass Installer', description: 'lorem ipsum', location: 'Kansas City, MO', department: 'Public Relations', date: '16/09/17' },
              { id: '4', title: 'Wheat Inspector', description: 'lorem ipsum', location: 'Red Bank, NJ', department: 'Quality Assurance', date: '12/06/16' },
              { id: '5', title: 'Executive Officer, Special Warfare Team', description: 'lorem ipsum', location: 'Irving, TX', department: 'Public Relations', date: '19/03/18' },
              { id: '6', title: 'Wildlife Control Agent', description: 'lorem ipsum', location: 'Irvine, CA', department: 'Sales and Marketing', date: '07/01/17' },
              { id: '7', title: 'Arresting Gear Operator', description: 'lorem ipsum', location: 'Charlotte, NC', department: 'Asset Management', date: '04/09/17' },
              { id: '8', title: 'Arresting Gear Operator', description: 'lorem ipsum', location: 'Chandler, AZ', department: 'Tech Support', date: '01/04/17' },
              { id: '9', title: 'Biogeographer', description: 'lorem ipsum', location: 'Chicago, IL', department: 'Quality Assurance', date: '01/05/17' },
              { id: '10', title: 'LAN Systems Administrator', description: 'lorem ipsum', location: 'Scottsdale, AZ', department: 'Customer Relations', date: '29/04/18' },
              { id: '11', title: 'Copper Plater', description: 'lorem ipsum', location: 'Irving, TX', department: 'Tech Support', date: '17/08/17' },
              { id: '12', title: 'Leaded Glass Installer', description: 'lorem ipsum', location: 'Rockville, MD', department: 'Sales and Marketing', date: '02/11/16' },
              { id: '13', title: 'Line Cook', description: 'lorem ipsum', location: 'Chandler, AZ', department: 'Advertising', date: '02/12/17' },
              { id: '14', title: 'Special Education Teaching Assistant', description: 'lorem ipsum', location: 'Red Bank, NJ', department: 'Payroll', date: '02/05/17' },
              { id: '15', title: 'Clarinetist', description: 'lorem ipsum', location: 'Melville, NY', department: 'Payroll', date: '30/05/17' },
              { id: '16', title: 'Arresting Gear Operator', description: 'lorem ipsum', location: 'Henderson, NV', department: 'Payroll', date: '23/02/18' },
              { id: '17', title: 'Wheat Inspector', description: 'lorem ipsum', location: 'Red Bank, NJ', department: 'Tech Support', date: '12/08/16' },
              { id: '18', title: 'Wildlife Control Agent', description: 'lorem ipsum', location: 'Melville, NY', department: 'Payroll', date: '03/05/17' },
              { id: '19', title: 'Print Retoucher', description: 'lorem ipsum', location: 'Chicago, IL', department: 'Sales and Marketing', date: '19/06/16' },
              { id: '20', title: 'Mathematical Statistician', description: 'lorem ipsum', location: 'Scottsdale, AZ', department: 'Tech Support', date: '10/07/16' }
            ];
          },
          filterJobs: function(event) {
            app.jobs = app.jobs.filter(function (job) {
              return job.location.includes(app.checkedLocations);
            });

            // filterJobs: function(event) {
            //     app.jobs = app.jobs.filter( function( location ) {
            //       return !app.checkedLocations.includes( location );
            //     } );
          }
        }
    });



   };


   return { init, app };

})();

(function(){
  careers.taleo.init();
})();
#app {
  padding: 25px;
}
#app ul {
  margin-left: 0;
  padding: 0;
}
#app ul li {
  list-style: none;
}
<link href=".0.0-alpha.6/css/bootstrap.min.css" rel="stylesheet"/>
<script src=".1.10/vue.min.js"></script>

<div id="app">

  <div class="container-fluid">
    <div class="row">
      <div class="col-md-3">
        <h3>Locations</h3>
        <ul>
          <li v-for="location in locations">
           <input type="checkbox" v-model="checkedLocations" v-on:click="filterJobs" v-bind:value="location" />  {{location}}
          </li>
        </ul>
        <span>Checked locations: {{ checkedLocations }}</span>
      </div>
      <div class="col-md-9">
         <div class="jobs">
           <div class="job" v-for="job in jobs">
             <div class="card" style="margin: 5px 0">
               <div class="card-block">
                 <h4 class="card-title">
                   {{ job.title }}
                 </h4>
                 <small class="pull-right text-muted" style="font-size: 12x">
                   {{job.date}}
                 </small>
                 <p class="card-text">
                    <!-- {{job.description}} -->
                 </p>
                 <button class="btn btn-sm btn-primary">View</button>
               </div>
             </div>
           </div>
         </div>
      </div>
    </div>
  </div>

</div>

This is my first VueJS project (making the move from jQuery) and I am trying to filter a grid with multiple checkboxes. As you can see from the JavaScript, I have a filterJobs function that filters the array with values set from whats checked (the v-model="checkedLocations"). array.includes appears to filter on a single value and I'd like to filter multiple values. I don't want to pop or slice the array because if they uncheck a location the they'll be gone and won't rebind

let careers = careers || {};

 careers.taleo = (function($){

   let app;

   let init = function() {

    app = new Vue({
      el: '#app',
      data: {
        locations: ['Scottsdale, AZ','Chandler, AZ','Irvine, CA','Denver, CO','Chicago, IL','Rockville, MD','Kansas City, MO','Charlotte, NC','Red Bank, NJ','Henderson, NV','Melville, NY','Allentown, PA','Irving, TX'],
        jobs: null,
        checkedLocations: []
      },
      created: function () {
        this.fetchData();
      },
      methods: {
          fetchData: function () {
            this.jobs = [
              { id: '1', title: 'Circuit Court Clerk', description: 'lorem ipsum', location: 'Charlotte, NC', department: 'Sales and Marketing', date: '23/10/17' },
              { id: '2', title: 'Tie Buyer', description: 'lorem ipsum', location: 'Irvine, CA', department: 'Media Relations', date: '21/10/16' },
              { id: '3', title: 'Leaded Glass Installer', description: 'lorem ipsum', location: 'Kansas City, MO', department: 'Public Relations', date: '16/09/17' },
              { id: '4', title: 'Wheat Inspector', description: 'lorem ipsum', location: 'Red Bank, NJ', department: 'Quality Assurance', date: '12/06/16' },
              { id: '5', title: 'Executive Officer, Special Warfare Team', description: 'lorem ipsum', location: 'Irving, TX', department: 'Public Relations', date: '19/03/18' },
              { id: '6', title: 'Wildlife Control Agent', description: 'lorem ipsum', location: 'Irvine, CA', department: 'Sales and Marketing', date: '07/01/17' },
              { id: '7', title: 'Arresting Gear Operator', description: 'lorem ipsum', location: 'Charlotte, NC', department: 'Asset Management', date: '04/09/17' },
              { id: '8', title: 'Arresting Gear Operator', description: 'lorem ipsum', location: 'Chandler, AZ', department: 'Tech Support', date: '01/04/17' },
              { id: '9', title: 'Biogeographer', description: 'lorem ipsum', location: 'Chicago, IL', department: 'Quality Assurance', date: '01/05/17' },
              { id: '10', title: 'LAN Systems Administrator', description: 'lorem ipsum', location: 'Scottsdale, AZ', department: 'Customer Relations', date: '29/04/18' },
              { id: '11', title: 'Copper Plater', description: 'lorem ipsum', location: 'Irving, TX', department: 'Tech Support', date: '17/08/17' },
              { id: '12', title: 'Leaded Glass Installer', description: 'lorem ipsum', location: 'Rockville, MD', department: 'Sales and Marketing', date: '02/11/16' },
              { id: '13', title: 'Line Cook', description: 'lorem ipsum', location: 'Chandler, AZ', department: 'Advertising', date: '02/12/17' },
              { id: '14', title: 'Special Education Teaching Assistant', description: 'lorem ipsum', location: 'Red Bank, NJ', department: 'Payroll', date: '02/05/17' },
              { id: '15', title: 'Clarinetist', description: 'lorem ipsum', location: 'Melville, NY', department: 'Payroll', date: '30/05/17' },
              { id: '16', title: 'Arresting Gear Operator', description: 'lorem ipsum', location: 'Henderson, NV', department: 'Payroll', date: '23/02/18' },
              { id: '17', title: 'Wheat Inspector', description: 'lorem ipsum', location: 'Red Bank, NJ', department: 'Tech Support', date: '12/08/16' },
              { id: '18', title: 'Wildlife Control Agent', description: 'lorem ipsum', location: 'Melville, NY', department: 'Payroll', date: '03/05/17' },
              { id: '19', title: 'Print Retoucher', description: 'lorem ipsum', location: 'Chicago, IL', department: 'Sales and Marketing', date: '19/06/16' },
              { id: '20', title: 'Mathematical Statistician', description: 'lorem ipsum', location: 'Scottsdale, AZ', department: 'Tech Support', date: '10/07/16' }
            ];
          },
          filterJobs: function(event) {
            app.jobs = app.jobs.filter(function (job) {
              return job.location.includes(app.checkedLocations);
            });

            // filterJobs: function(event) {
            //     app.jobs = app.jobs.filter( function( location ) {
            //       return !app.checkedLocations.includes( location );
            //     } );
          }
        }
    });



   };


   return { init, app };

})();

(function(){
  careers.taleo.init();
})();
#app {
  padding: 25px;
}
#app ul {
  margin-left: 0;
  padding: 0;
}
#app ul li {
  list-style: none;
}
<link href="https://cdnjs.cloudflare./ajax/libs/twitter-bootstrap/4.0.0-alpha.6/css/bootstrap.min.css" rel="stylesheet"/>
<script src="https://cdnjs.cloudflare./ajax/libs/vue/2.1.10/vue.min.js"></script>

<div id="app">

  <div class="container-fluid">
    <div class="row">
      <div class="col-md-3">
        <h3>Locations</h3>
        <ul>
          <li v-for="location in locations">
           <input type="checkbox" v-model="checkedLocations" v-on:click="filterJobs" v-bind:value="location" />  {{location}}
          </li>
        </ul>
        <span>Checked locations: {{ checkedLocations }}</span>
      </div>
      <div class="col-md-9">
         <div class="jobs">
           <div class="job" v-for="job in jobs">
             <div class="card" style="margin: 5px 0">
               <div class="card-block">
                 <h4 class="card-title">
                   {{ job.title }}
                 </h4>
                 <small class="pull-right text-muted" style="font-size: 12x">
                   {{job.date}}
                 </small>
                 <p class="card-text">
                    <!-- {{job.description}} -->
                 </p>
                 <button class="btn btn-sm btn-primary">View</button>
               </div>
             </div>
           </div>
         </div>
      </div>
    </div>
  </div>

</div>

https://codepen.io/neil/pen/WjXrxx

Share Improve this question asked May 11, 2017 at 21:26 user147215user147215 2
  • You don't need to move from jQuery – it works very well with Vue, especially, when you want to use Ajax. – Staszek Commented May 11, 2017 at 21:49
  • What I mean by move from jQuery, is solely using jQuery to build interactive interfaces like this. – user147215 Commented May 12, 2017 at 15:04
Add a ment  | 

2 Answers 2

Reset to default 6

Use a puted value for your filtered locations.

puted:{
  filteredJobs(){
    // if there are no checked locations, return everything.
    // You could remove this if you only want to return 
    // checked locations.
    if (!this.checkedLocations.length)
       return this.jobs

     return this.jobs.filter(j => this.checkedLocations.includes(j.location))
  }
}

And modify your template.

<div class="job" v-for="job in filteredJobs">

While also removing your filterJobs method.

Example.

Basically you needed to flip your filter to

this.checkedLocations.includes(job.location). 

Also, you don't want to be changing your data every time you filter because you are bleeding data. Using a puted value is more idiomatic for Vue however.

Use v-if in line where you list jobs:

<div class="job" v-if=filterJobs(job) v-for="job in jobs">

and use method filterJobs like that:

filterJobs: function(data) {
        if (this.checkedLocations.length == 0) return true;
        return this.checkedLocations.includes(data.location);
}

Edited code

本文标签: javascriptCheckbox filtering with VueJSStack Overflow