Thu Dec 3 00:12:02 UTC 2009 pix@kepibu.org * Add sibling and adjacent combinators diff -rN -u old-Oh, Ducks!/selectors.lisp new-Oh, Ducks!/selectors.lisp --- old-Oh, Ducks!/selectors.lisp 2015-12-09 14:27:37.000000000 +0000 +++ new-Oh, Ducks!/selectors.lisp 2015-12-09 14:27:37.000000000 +0000 @@ -51,8 +51,10 @@ (defun parse-selector (selector) (match-case (selector) ;; combinators - #+TODO (#T(regexp$ "[ ]*[~][ ]*" ()) (list (make-instance 'sibling-combinator :matcher (parse-selector &rest)))) - #+TODO (#T(regexp$ "[ ]*[+][ ]*" ()) (list (make-instance 'adjacent-combinator :matcher (parse-selector &rest)))) + (#T(regexp$ "[ ]*[~][ ]*" ()) + (list (make-instance 'sibling-combinator :matcher (parse-selector &rest)))) + (#T(regexp$ "[ ]*[+][ ]*" ()) + (list (make-instance 'adjacent-combinator :matcher (parse-selector &rest)))) (#T(regexp$ "[ ]*[>][ ]*" ()) (list (make-instance 'child-combinator :matcher (parse-selector &rest)))) (#T(regexp$ "[ ]+" ()) @@ -143,10 +145,18 @@ (defmethod element-matches-p (element (selector descendant-combinator)) (some (rcurry #'element-matches-p (matcher selector)) (element-ancestors element))) -#+TODO (defmethod element-matches-p (element (selector adjacent-combinator)) - ...) + (let* ((parent (element-parent element)) + (siblings (element-children parent)) + (ourpos (position element siblings :test #'eq))) + (and ourpos + (> ourpos 0) + (element-matches-p (elt siblings (1- ourpos)) (matcher selector))))) -#+TODO (defmethod element-matches-p (element (selector sibling-combinator)) - ...) + (let* ((parent (element-parent element)) + (siblings (element-children parent)) + (ourpos (position element siblings :test #'eq))) + (and ourpos + (> ourpos 0) + (find-if (rcurry #'element-matches-p (matcher selector)) siblings :end ourpos)))) diff -rN -u old-Oh, Ducks!/tests.lisp new-Oh, Ducks!/tests.lisp --- old-Oh, Ducks!/tests.lisp 2015-12-09 14:27:37.000000000 +0000 +++ new-Oh, Ducks!/tests.lisp 2015-12-09 14:27:37.000000000 +0000 @@ -59,6 +59,17 @@ "
I do not like cheese.
I like cheese.
") (values div)) +(match (#T(html (:model dom) + ("b + i" . ?i)) + "
I really like cheese. Do you not dislike cheese?
") + (values i)) + +(match (#T(html (:model dom) + ("b ~ i" . ?i)) + "
I really like cheese. Do you not dislike cheese?
") + (values i)) + + #+LATER? (match (#t(html ("div::content" . #t(regexp+ "^f(o+)" (?o)))) "
barbaz
fooooooobar
")