public function filter($value)
        {
            // start by stripping the comments, if necessary
            if(!$this->allowComments) {
                $value = preg_replace('/<!\-\-.*\-\->/U', '', $value);
            }

            // strip unallowed tags
            $allowed = '';
            foreach($this->allowedTags as $tag) {
                $allowed .= "<{$tag}>";
            }
            $value = strip_tags($value, $allowed);

            // strip unallowed attributes - only if there are allowed tags,
            // otherwise all attributes have already been removed with the tags
            if(!empty($this->allowedTags)) {
                $allowed = $this->allowedAttributes;
                do {
                    $old   = $value;
                    $value = preg_replace_callback('/<[a-zA-Z]+ *(([a-zA-Z_:][\-a-zA-Z0-9_:\.]+) *=.*["\'].*["\']).*>/U', function($matches) use($allowed) {
                        if(in_array($matches[2], $allowed)) {
                            return $matches[0];
                        } else {
                            return repl(' ' . $matches[1], '', $matches[0]);
                        }
                    }, $value);
                } while($old != $value);
            }

            // we're left with the filtered value
            return $value;
        }