Commit bf146431 by Aaron Leung

Don't need these files anymore.

parent 3cfac648
#define SASS_NODE_INCLUDED
#include <vector>
#include <sstream>
#include "values.hpp"
#include <iostream>
namespace Sass {
using std::string;
using std::vector;
using std::stringstream;
using std::cerr; using std::endl;
struct Node {
enum Type {
root,
ruleset,
propset,
selector_group,
selector,
selector_combinator,
simple_selector_sequence,
backref,
simple_selector,
type_selector,
class_selector,
id_selector,
pseudo,
pseudo_negation,
functional_pseudo,
attribute_selector,
block,
rule,
property,
nil,
comma_list,
space_list,
disjunction,
conjunction,
relation,
eq,
neq,
gt,
gte,
lt,
lte,
expression,
add,
sub,
term,
mul,
div,
factor,
unary_plus,
unary_minus,
values,
value,
identifier,
uri,
textual_percentage,
textual_dimension,
textual_number,
textual_hex,
color_name,
string_constant,
numeric_percentage,
numeric_dimension,
number,
numeric_color,
boolean,
important,
value_schema,
string_schema,
css_import,
function_call,
mixin,
parameters,
expansion,
arguments,
variable,
assignment,
comment,
none,
flags
};
Type type;
unsigned int line_number;
bool has_children;
bool has_statements;
bool has_blocks;
bool has_expansions;
bool has_backref;
bool from_variable;
bool eval_me;
bool unquoted;
union {
Token token;
mutable vector<Node>* children;
Dimension dimension;
double numeric_value;
bool boolean_value;
} content;
const char* file_name;
static size_t allocations;
static size_t destructed;
void clear()
{
type = none; line_number = 0; file_name = 0;
has_children = false; has_statements = false; has_blocks = false;
has_expansions = false; has_backref = false; from_variable = false;
eval_me = false; unquoted = false;
}
size_t size() const
{ return content.children->size(); }
Node& operator[](const size_t i) const
{ return content.children->at(i); }
Node& at(const size_t i) const
{ return content.children->at(i); }
Node& operator<<(const Node& n)
{
content.children->push_back(n);
return *this;
}
bool is_numeric() const
{
switch (type)
{
case number:
case numeric_percentage:
case numeric_dimension:
return true;
break;
default:
return false;
}
}
double numeric_value() const
{
switch (type)
{
case number:
case numeric_percentage:
return content.numeric_value;
case numeric_dimension:
return content.dimension.numeric_value;
default:
break;
// throw an exception?
}
}
void set_numeric_value(double v)
{
switch (type)
{
case number:
case numeric_percentage:
content.numeric_value = v;
case numeric_dimension:
content.dimension.numeric_value = v;
default:
break;
// throw an exception?
}
}
Node& operator+=(const Node& n)
{
for (size_t i = 0; i < n.size(); ++i) {
content.children->push_back(n[i]);
}
return *this;
}
bool operator==(const Node& rhs) const;
bool operator!=(const Node& rhs) const;
bool operator<(const Node& rhs) const;
bool operator<=(const Node& rhs) const;
bool operator>(const Node& rhs) const;
bool operator>=(const Node& rhs) const;
string to_string(const string& prefix) const;
void echo(stringstream& buf, size_t depth = 0);
void emit_nested_css(stringstream& buf,
size_t depth,
const vector<string>& prefixes);
void emit_nested_css(stringstream& buf, size_t depth);
void emit_propset(stringstream& buf, size_t depth, const string& prefix);
void emit_expanded_css(stringstream& buf, const string& prefix);
Node clone(vector<vector<Node>*>& registry) const;
void flatten();
Node()
{ clear(); }
Node(Type t) // flags or booleans
{ clear(); type = t; }
Node(Type t, vector<vector<Node>*>& registry, unsigned int ln, size_t s = 0) // nodes with children
{
clear();
type = t;
line_number = ln;
content.children = new vector<Node>;
registry.push_back(content.children);
content.children->reserve(s);
has_children = true;
++allocations;
}
Node(Type t, unsigned int ln, const Token& tok) // nodes with a single token
{
clear();
type = t;
line_number = ln;
content.token = tok;
}
Node(unsigned int ln, double val) // numeric values
{
clear();
type = number;
line_number = ln;
content.numeric_value = val;
}
Node(unsigned int ln, double val, const Token& tok) // dimensions
{
clear();
type = numeric_dimension;
line_number = ln;
content.dimension = Dimension();
content.dimension.numeric_value = val;
content.dimension.unit = tok.begin;
}
Node(vector<vector<Node>*>& registry, unsigned int ln, double r, double g, double b, double a = 1.0) // colors
{
clear();
type = numeric_color;
line_number = ln;
content.children = new vector<Node>;
registry.push_back(content.children);
content.children->reserve(4);
content.children->push_back(Node(ln, r));
content.children->push_back(Node(ln, g));
content.children->push_back(Node(ln, b));
content.children->push_back(Node(ln, a));
has_children = true;
++allocations;
}
~Node() { ++destructed; }
};
}
#include <iostream>
#include <iomanip>
#include <string>
#include <cctype>
#include <cstdlib>
#include <cmath>
#include "node.hpp"
#include "error.hpp"
using std::string;
using std::stringstream;
using std::cout;
using std::cerr;
using std::endl;
namespace Sass {
bool Node::operator==(const Node& rhs) const
{
if (type != rhs.type) return false;
switch (type)
{
case comma_list:
case space_list:
case expression:
case term: {
for (size_t i = 0; i < size(); ++i) {
if (at(i) == rhs[i]) continue;
else return false;
}
return true;
} break;
case variable:
case identifier:
case uri:
case textual_percentage:
case textual_dimension:
case textual_number:
case textual_hex:
case string_constant: {
return content.token.unquote() == rhs.content.token.unquote();
} break;
case number:
case numeric_percentage: {
return numeric_value() == rhs.numeric_value();
} break;
case numeric_dimension: {
if (Token::make(content.dimension.unit, Prelexer::identifier(content.dimension.unit)) ==
Token::make(rhs.content.dimension.unit, Prelexer::identifier(rhs.content.dimension.unit))) {
return numeric_value() == rhs.numeric_value();
}
else {
return false;
}
} break;
case boolean: {
return content.boolean_value == rhs.content.boolean_value;
} break;
default: {
return true;
} break;
}
}
bool Node::operator!=(const Node& rhs) const
{ return !(*this == rhs); }
bool Node::operator<(const Node& rhs) const
{
if (type == number && rhs.type == number ||
type == numeric_percentage && rhs.type == numeric_percentage) {
return numeric_value() < rhs.numeric_value();
}
else if (type == numeric_dimension && rhs.type == numeric_dimension) {
if (Token::make(content.dimension.unit, Prelexer::identifier(content.dimension.unit)) ==
Token::make(rhs.content.dimension.unit, Prelexer::identifier(rhs.content.dimension.unit))) {
return numeric_value() < rhs.numeric_value();
}
else {
throw Error(Error::evaluation, line_number, file_name, "incompatible units");
}
}
else {
throw Error(Error::evaluation, line_number, file_name, "incomparable types");
}
}
bool Node::operator<=(const Node& rhs) const
{ return *this < rhs || *this == rhs; }
bool Node::operator>(const Node& rhs) const
{ return !(*this <= rhs); }
bool Node::operator>=(const Node& rhs) const
{ return !(*this < rhs); }
}
#include "values.hpp"
namespace Sass {
// Token::Token() : begin(0), end(0) { }
// Token::Token(const char* begin, const char* end)
// : begin(begin), end(end) { }
string Token::unquote() const {
string result;
const char* p = begin;
if (*begin == '\'' || *begin == '"') {
++p;
while (p < end) {
if (*p == '\\') {
switch (*(++p)) {
case 'n': result += '\n'; break;
case 't': result += '\t'; break;
case 'b': result += '\b'; break;
case 'r': result += '\r'; break;
case 'f': result += '\f'; break;
case 'v': result += '\v'; break;
case 'a': result += '\a'; break;
case '\\': result += '\\'; break;
default: result += *p; break;
}
}
else if (p == end - 1) {
return result;
}
else {
result += *p;
}
++p;
}
return result;
}
else {
while (p < end) {
result += *(p++);
}
return result;
}
}
void Token::unquote_to_stream(std::stringstream& buf) const {
const char* p = begin;
if (*begin == '\'' || *begin == '"') {
++p;
while (p < end) {
if (*p == '\\') {
switch (*(++p)) {
case 'n': buf << '\n'; break;
case 't': buf << '\t'; break;
case 'b': buf << '\b'; break;
case 'r': buf << '\r'; break;
case 'f': buf << '\f'; break;
case 'v': buf << '\v'; break;
case 'a': buf << '\a'; break;
case '\\': buf << '\\'; break;
default: buf << *p; break;
}
}
else if (p == end - 1) {
return;
}
else {
buf << *p;
}
++p;
}
return;
}
else {
while (p < end) {
buf << *(p++);
}
return;
}
}
bool Token::operator<(const Token& rhs) const
{
const char* first1 = begin;
const char* last1 = end;
const char* first2 = rhs.begin;
const char* last2 = rhs.end;
while (first1!=last1)
{
if (first2==last2 || *first2<*first1) return false;
else if (*first1<*first2) return true;
first1++; first2++;
}
return (first2!=last2);
}
bool Token::operator==(const Token& rhs) const
{
if (length() != rhs.length()) return false;
if ((begin[0] == '"' || begin[0] == '\'') &&
(rhs.begin[0] == '"' || rhs.begin[0] == '\''))
{ return unquote() == rhs.unquote(); }
const char* p = begin;
const char* q = rhs.begin;
for (; p < end; ++p, ++q) if (*p != *q) return false;
return true;
}
}
\ No newline at end of file
#include <string>
#include <sstream>
#include <cstring>
#ifndef SASS_PRELEXER_INCLUDED
#include "prelexer.hpp"
#endif
namespace Sass {
using std::string;
struct Token {
const char* begin;
const char* end;
// Token();
// Token(const char* begin, const char* end);
size_t length() const
{ return end - begin; }
inline operator string() const
{ return string(begin, end - begin); }
string to_string() const
{ return string(begin, end - begin); }
string unquote() const;
void unquote_to_stream(std::stringstream& buf) const;
bool operator<(const Token& rhs) const;
bool operator==(const Token& rhs) const;
operator bool()
{ return begin && end && begin >= end; }
static Token make()
{
Token t;
t.begin = 0;
t.end = 0;
return t;
}
static Token make(const char* s)
{
Token t;
t.begin = s;
t.end = s + std::strlen(s);
return t;
}
static Token make(const char* b, const char* e)
{
Token t;
t.begin = b;
t.end = e;
return t;
}
};
struct Dimension {
double numeric_value;
const char* unit;
};
}
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment