223 lines
6.0 KiB
Python
Raw Normal View History

2012-04-03 12:41:34 +00:00
# -*- coding: utf8 -*-
2012-01-28 14:52:09 +00:00
"""
2012-04-03 12:41:34 +00:00
.. module:: lesscpy.plib.call
:synopsis: Call parse node
Copyright (c)
See LICENSE for details.
.. moduleauthor:: Jóhann T. Maríusson <jtm@robot.is>
2012-01-28 14:52:09 +00:00
"""
2012-03-24 17:23:14 +00:00
import re, math
2012-03-25 13:25:05 +00:00
from urllib.parse import quote as urlquote, urlparse
2012-02-19 20:38:19 +00:00
from .node import Node
2012-02-25 17:08:08 +00:00
import lesscpy.lessc.utility as utility
2012-02-27 19:22:52 +00:00
import lesscpy.lessc.color as Color
2012-03-25 13:25:05 +00:00
from lesscpy.lib.colors import lessColors
2012-02-27 19:22:52 +00:00
2012-02-19 20:38:19 +00:00
class Call(Node):
2012-04-03 12:41:34 +00:00
"""Call node. Node represents a function call.
All builtin none-color functions are in this node.
This node attempts calls on built-ins and lets non-builtins
through.
2012-05-07 13:14:55 +00:00
increment(3px) --> 4px
unknown(3px) --> unknown(3px)
2012-04-03 12:41:34 +00:00
"""
2012-02-25 17:08:08 +00:00
def parse(self, scope):
2012-04-03 12:41:34 +00:00
"""Parse Node within scope.
the functions ~( and e( map to self.escape
and %( maps to self.sformat
args:
2012-04-03 13:36:08 +00:00
scope (Scope): Current scope
2012-03-24 17:23:14 +00:00
"""
name = ''.join(self.tokens[0])
parsed = self.process(self.tokens[1:], scope)
2012-04-06 19:23:22 +00:00
if name == '%(':
name = 'sformat'
elif name in ('~', 'e'):
name = 'escape'
color = Color.Color()
args = [t for t in parsed
if type(t) is not str or t not in '(),']
if hasattr(self, name):
try:
return getattr(self, name)(*args)
except ValueError:
pass
if hasattr(color, name):
try:
result = getattr(color, name)(*args)
2012-03-18 19:25:05 +00:00
try:
return result + ' '
except TypeError:
return result
except ValueError:
pass
return name + ''.join([p for p in parsed])
2012-02-27 19:22:52 +00:00
2012-04-03 12:41:34 +00:00
def escape(self, string, *args):
"""Less Escape.
args:
string (str): string to escape
returns:
str
"""
return utility.destring(string.strip('~'))
def sformat(self, string, *args):
""" String format.
args:
string (str): string to format
args (list): format options
returns:
str
"""
if not args:
raise SyntaxError('Not enough arguments...')
format = string
2012-02-27 19:22:52 +00:00
items = []
m = re.findall('(%[asdA])', format)
2012-04-03 12:41:34 +00:00
i = 0
2012-02-27 19:22:52 +00:00
for n in m:
v = {
'%A' : urlquote,
'%s' : utility.destring,
}.get(n, str)(args[i])
items.append(v)
i += 1
format = format.replace('%A', '%s')
2012-05-07 09:37:07 +00:00
format = format.replace('%d', '%s')
2012-02-27 19:22:52 +00:00
return format % tuple(items)
2012-04-03 12:41:34 +00:00
def isnumber(self, string, *args):
"""Is number
args:
string (str): match
returns:
bool
2012-03-25 13:25:05 +00:00
"""
try:
2012-04-03 12:41:34 +00:00
n, u = utility.analyze_number(string)
2012-03-25 13:25:05 +00:00
except SyntaxError as e:
return False
return True
2012-04-03 12:41:34 +00:00
def iscolor(self, string, *args):
"""Is color
args:
string (str): match
returns:
bool
"""
return (string in lessColors)
2012-03-25 13:25:05 +00:00
2012-04-03 12:41:34 +00:00
def isurl(self, string, *args):
"""Is url
args:
string (str): match
returns:
bool
"""
arg = utility.destring(string)
2012-05-07 13:14:55 +00:00
regex = re.compile(r'^(?:http|ftp)s?://' # http:// or https://
r'(?:(?:[A-Z0-9](?:[A-Z0-9-]{0,61}[A-Z0-9])?\.)+'
r'(?:[A-Z]{2,6}\.?|[A-Z0-9-]{2,}\.?)|' #domain...
r'localhost|' #localhost...
r'\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3})' # ...or ip
r'(?::\d+)?' # optional port
2012-03-25 13:25:05 +00:00
r'(?:/?|[/?]\S+)$', re.IGNORECASE)
return regex.match(arg)
2012-04-03 12:41:34 +00:00
def isstring(self, string, *args):
"""Is string
args:
string (str): match
returns:
bool
2012-03-25 13:25:05 +00:00
"""
regex = re.compile(r'\'[^\']*\'|"[^"]*"')
2012-04-03 12:41:34 +00:00
return regex.match(string)
2012-03-25 13:25:05 +00:00
2012-04-03 12:41:34 +00:00
def iskeyword(self, string, *args):
"""Is less keyword
args:
string (str): match
returns:
bool
"""
return (string in ('when', 'and', 'not'))
2012-03-25 13:25:05 +00:00
2012-04-03 12:41:34 +00:00
def increment(self, value, *args):
2012-02-27 19:22:52 +00:00
""" Increment function
2012-04-03 12:41:34 +00:00
args:
value (str): target
returns:
str
2012-02-27 19:22:52 +00:00
"""
2012-04-03 12:41:34 +00:00
n, u = utility.analyze_number(value)
2012-02-27 19:22:52 +00:00
return utility.with_unit(n+1, u)
2012-04-03 12:41:34 +00:00
def decrement(self, value, *args):
2012-02-27 19:22:52 +00:00
""" Decrement function
2012-04-03 12:41:34 +00:00
args:
value (str): target
returns:
str
2012-02-27 19:22:52 +00:00
"""
2012-04-03 12:41:34 +00:00
n, u = utility.analyze_number(value)
2012-02-27 19:22:52 +00:00
return utility.with_unit(n-1, u)
def add(self, *args):
""" Add integers
2012-04-03 12:41:34 +00:00
args:
args (list): target
returns:
str
2012-02-27 19:22:52 +00:00
"""
2012-04-03 12:41:34 +00:00
if(len(args) <= 1): return 0
2012-02-27 19:22:52 +00:00
return sum([int(v) for v in args])
2012-04-03 12:41:34 +00:00
def round(self, value, *args):
2012-02-27 19:22:52 +00:00
""" Round number
2012-04-03 12:41:34 +00:00
args:
value (str): target
returns:
str
2012-02-27 19:22:52 +00:00
"""
2012-04-03 12:41:34 +00:00
n, u = utility.analyze_number(value)
2012-02-27 19:22:52 +00:00
return utility.with_unit(round(float(n)), u)
2012-03-24 17:23:14 +00:00
2012-04-03 12:41:34 +00:00
def ceil(self, value, *args):
2012-03-24 18:33:19 +00:00
""" Ceil number
2012-04-03 12:41:34 +00:00
args:
value (str): target
returns:
str
2012-03-24 17:23:14 +00:00
"""
2012-04-03 12:41:34 +00:00
n, u = utility.analyze_number(value)
2012-03-24 17:23:14 +00:00
return utility.with_unit(math.ceil(n), u)
2012-04-03 12:41:34 +00:00
def floor(self, value, *args):
2012-03-24 18:33:19 +00:00
""" Floor number
2012-04-03 12:41:34 +00:00
args:
value (str): target
returns:
str
2012-03-24 17:23:14 +00:00
"""
2012-04-03 12:41:34 +00:00
n, u = utility.analyze_number(value)
2012-03-24 17:23:14 +00:00
return utility.with_unit(math.floor(n), u)
2012-04-03 12:41:34 +00:00
def percentage(self, value, *args):
2012-03-24 18:33:19 +00:00
""" Return percentage value
2012-04-03 12:41:34 +00:00
args:
value (str): target
returns:
str
2012-03-24 17:23:14 +00:00
"""
2012-04-03 12:41:34 +00:00
n, u = utility.analyze_number(value)
2012-03-24 17:23:14 +00:00
n = int(n * 100.0)
u = '%'
return utility.with_unit(n, u)