2
0
Evan You 12 жил өмнө
parent
commit
607e197a08

+ 1 - 1
examples/todomvc/index.html

@@ -28,7 +28,7 @@
                 <ul id="todo-list">
                     <li
                         class="todo"
-                        v-repeat="filteredTodos"
+                        v-repeat="todos | filterTodos"
                         v-class="
                             completed : completed,
                             editing   : this == editedTodo

+ 7 - 4
examples/todomvc/js/app.js

@@ -44,14 +44,17 @@
             }
         },
 
+        filters: {
+            filterTodos: function (todos) {
+                return todos.filter(filters[this.filter]);
+            }
+        },
+
         // computed property
         // http://vuejs.org/guide/computed.html
         computed: {
-            filteredTodos: function () {
-                return this.todos.filter(filters[this.filter]);
-            },
             remaining: function () {
-                return this.todos.filter(filters.active).length
+                return this.todos.filter(filters.active).length;
             },
             allDone: {
                 $get: function () {

+ 0 - 2
src/exp-parser.js

@@ -177,8 +177,6 @@ exports.parse = function (exp, compiler, data, filters) {
         return strings[i]
     }
 
-    console.log(body)
-
     return makeGetter(body, exp)
 }
 

+ 2 - 0
src/main.js

@@ -31,6 +31,8 @@ assetTypes.forEach(function (type) {
             value = utils.toFragment(value)
         } else if (type === 'component') {
             value = utils.toConstructor(value)
+        } else if (type === 'filter') {
+            utils.checkFilter(value)
         }
         hash[id] = value
         return this

+ 17 - 0
src/utils.js

@@ -3,6 +3,7 @@ var config    = require('./config'),
     win       = window,
     console   = win.console,
     timeout   = win.setTimeout,
+    THIS_RE   = /[^\w]this\./,
     hasClassList = 'classList' in document.documentElement,
     ViewModel // late def
 
@@ -164,6 +165,16 @@ var utils = module.exports = {
                 : null
     },
 
+    /**
+     *  Check if a filter function contains references to `this`
+     *  If yes, mark it as a computed filter.
+     */
+    checkFilter: function (filter) {
+        if (THIS_RE.test(filter.toString())) {
+            filter.computed = true
+        }
+    },
+
     /**
      *  convert certain option values to the desired format.
      */
@@ -171,6 +182,7 @@ var utils = module.exports = {
         var components = options.components,
             partials   = options.partials,
             template   = options.template,
+            filters    = options.filters,
             key
         if (components) {
             for (key in components) {
@@ -182,6 +194,11 @@ var utils = module.exports = {
                 partials[key] = utils.toFragment(partials[key])
             }
         }
+        if (filters) {
+            for (key in filters) {
+                utils.checkFilter(filters[key])
+            }
+        }
         if (template) {
             options.template = utils.toFragment(template)
         }

+ 3 - 1
test/unit/specs/directive.js

@@ -5,7 +5,9 @@ describe('Directive', function () {
 
     var compiler = {
         options: {},
-        getOption: function () {},
+        getOption: function (type, id) {
+            return Vue.options[type][id]
+        },
         vm: {
             constructor: {}
         }

+ 39 - 0
test/unit/specs/misc.js

@@ -168,4 +168,43 @@ describe('Misc Features', function () {
 
     })
 
+    describe('computed filter', function () {
+        
+        it('should process filter with `this` as computed', function (done) {
+            
+            var V = Vue.extend({
+                template: '<div class="plus">{{n | plus}}</div><div class="minus">{{n | minus}}</div>',
+                filters: {
+                    plus: function (v) {
+                        return v + this.a
+                    }
+                }
+            })
+
+            V.filter('minus', function (v) {
+                return v - this.a
+            })
+
+            var v = new V({
+                data: {
+                    a: 1,
+                    n: 1
+                }
+            })
+
+            assert.strictEqual(v.$el.querySelector('.plus').textContent, '2')
+            assert.strictEqual(v.$el.querySelector('.minus').textContent, '0')
+
+            v.a = 2
+
+            nextTick(function () {
+                assert.strictEqual(v.$el.querySelector('.plus').textContent, '3')
+                assert.strictEqual(v.$el.querySelector('.minus').textContent, '-1')
+                done()
+            })
+
+        })
+
+    })
+
 })