OLD | NEW |
---|---|
1 #!/usr/bin/env python | 1 #!/usr/bin/env python |
2 # Copyright 2016 The Chromium Authors. All rights reserved. | 2 # Copyright 2016 The Chromium Authors. All rights reserved. |
3 # Use of this source code is governed by a BSD-style license that can be | 3 # Use of this source code is governed by a BSD-style license that can be |
4 # found in the LICENSE file. | 4 # found in the LICENSE file. |
5 | 5 |
6 from collections import namedtuple | |
7 import math | 6 import math |
8 import sys | 7 import sys |
9 | 8 |
10 import in_generator | 9 import in_generator |
11 import template_expander | 10 import template_expander |
12 import make_style_builder | 11 import make_style_builder |
13 | 12 |
14 from name_utilities import camel_case | 13 from name_utilities import camel_case |
15 | 14 |
15 | |
16 class Field(object): | |
17 """ | |
18 The generated ComputedStyle object is made up of a series of Fields. | |
19 Each Field has a name, size, type, etc, and a bunch of attributes to | |
20 determine which methods it will be used in. | |
21 | |
22 A Field also has enough information to use any storage type in C++, such as | |
23 regular member variables, or more complex storage like vectors or hashmaps. | |
24 Almost all properties will have at least one Field, often more than one. | |
25 | |
26 Fields also fall into various families, which determine the logic that is | |
27 used to generate them. The available field families are: | |
28 - 'enum', for fields that store the values of an enum | |
29 - 'inherited_flag', for single-bit flags that store whether a property is | |
30 inherited by this style or set explicitly | |
31 """ | |
32 def __init__(self, field_family, **kwargs): | |
33 # Values common to all fields | |
34 # Name of field | |
35 self.name = kwargs.pop('name') | |
36 # Property field is for | |
37 self.property = kwargs.pop('property') | |
38 # Field storage type | |
39 self.type = kwargs.pop('type') | |
40 # Bits needed for storage | |
41 self.size = kwargs.pop('size') | |
42 # Default value for field | |
43 self.default_value = kwargs.pop('default_value') | |
44 # Method names | |
45 self.getter_method_name = kwargs.pop('getter_method_name') | |
46 self.setter_method_name = kwargs.pop('setter_method_name') | |
47 self.initial_method_name = kwargs.pop('initial_method_name') | |
48 self.resetter_method_name = kwargs.pop('resetter_method_name') | |
49 | |
50 # Field family: one of these must be true | |
51 self.is_enum = field_family == 'enum' | |
52 self.is_inherited_flag = field_family == 'inherited_flag' | |
53 assert self.is_enum or self.is_inherited_flag, 'Only one field family ca n be specified at a time' | |
meade_UTC10
2016/12/06 03:03:36
don't you want
assert !(self.is_enum and self.is_
sashab
2016/12/06 03:05:53
Oh nice lol :) Whoops
| |
54 | |
55 if self.is_enum: | |
56 # Enum-only fields | |
57 self.is_inherited_method_name = kwargs.pop('is_inherited_method_name ') | |
58 elif self.is_inherited_flag: | |
59 # Inherited flag-only fields | |
60 pass | |
meade_UTC10
2016/12/06 03:03:36
I assume there will be something here eventually?
sashab
2016/12/06 03:05:54
Yup, think its ok if I leave it there for now just
| |
61 | |
62 assert len(kwargs) == 0, 'Unexpected arguments provided to Field: ' + st r(kwargs) | |
63 | |
64 | |
16 class ComputedStyleBaseWriter(make_style_builder.StyleBuilderWriter): | 65 class ComputedStyleBaseWriter(make_style_builder.StyleBuilderWriter): |
17 def __init__(self, in_file_path): | 66 def __init__(self, in_file_path): |
18 super(ComputedStyleBaseWriter, self).__init__(in_file_path) | 67 super(ComputedStyleBaseWriter, self).__init__(in_file_path) |
19 self._outputs = { | 68 self._outputs = { |
20 'ComputedStyleBase.h': self.generate_base_computed_style_h, | 69 'ComputedStyleBase.h': self.generate_base_computed_style_h, |
21 'ComputedStyleBase.cpp': self.generate_base_computed_style_cpp, | 70 'ComputedStyleBase.cpp': self.generate_base_computed_style_cpp, |
22 'ComputedStyleBaseConstants.h': self.generate_base_computed_style_co nstants, | 71 'ComputedStyleBaseConstants.h': self.generate_base_computed_style_co nstants, |
23 } | 72 } |
24 | 73 |
25 # A map of enum name -> list of enum values | 74 # A map of enum name -> list of enum values |
26 self._computed_enums = {} | 75 self._computed_enums = {} |
27 for property in self._properties.values(): | 76 for property in self._properties.values(): |
28 if property['keyword_only']: | 77 if property['keyword_only']: |
29 enum_name = property['type_name'] | 78 enum_name = property['type_name'] |
30 # From the Blink style guide: Enum members should use InterCaps with an initial capital letter. [names-enum-members] | 79 # From the Blink style guide: Enum members should use InterCaps with an initial capital letter. [names-enum-members] |
31 enum_values = [camel_case(k) for k in property['keywords']] | 80 enum_values = [camel_case(k) for k in property['keywords']] |
32 self._computed_enums[enum_name] = enum_values | 81 self._computed_enums[enum_name] = enum_values |
33 | 82 |
34 # A list of fields for the generated class. | 83 # A list of all the fields to be generated. |
35 # TODO(sashab): Rename this to Member, and add better documentation for what this list is for, | |
36 # including asserts to show inter-field dependencies. | |
37 Field = namedtuple('Field', [ | |
38 # Name of field member variable | |
39 'name', | |
40 # Property field is for | |
41 'property', | |
42 # Field family: one of these must be true | |
43 'is_enum', | |
44 'is_inherited_flag', | |
45 # Field storage type | |
46 'type', | |
47 # Bits needed for storage | |
48 'size', | |
49 # Default value for field | |
50 'default_value', | |
51 # Method names | |
52 'getter_method_name', | |
53 'setter_method_name', | |
54 'initial_method_name', | |
55 'resetter_method_name', | |
56 'is_inherited_method_name', | |
57 ]) | |
58 | |
59 # A list of all the fields to be generated. Add new fields here. | |
60 self._fields = [] | 84 self._fields = [] |
61 for property in self._properties.values(): | 85 for property in self._properties.values(): |
62 if property['keyword_only']: | 86 if property['keyword_only']: |
63 property_name = property['upper_camel_name'] | 87 property_name = property['upper_camel_name'] |
64 if property['name_for_methods']: | 88 if property['name_for_methods']: |
65 property_name = property['name_for_methods'] | 89 property_name = property['name_for_methods'] |
66 property_name_lower = property_name[0].lower() + property_name[1 :] | 90 property_name_lower = property_name[0].lower() + property_name[1 :] |
67 | 91 |
68 # From the Blink style guide: Other data members should be prefi xed by "m_". [names-data-members] | 92 # From the Blink style guide: Other data members should be prefi xed by "m_". [names-data-members] |
69 field_name = 'm_' + property_name_lower | 93 field_name = 'm_' + property_name_lower |
70 bits_needed = math.log(len(property['keywords']), 2) | 94 bits_needed = math.log(len(property['keywords']), 2) |
71 type_name = property['type_name'] | 95 type_name = property['type_name'] |
72 | 96 |
73 assert property['initial_keyword'] is not None, \ | 97 assert property['initial_keyword'] is not None, \ |
74 ('MakeComputedStyleBase requires an initial keyword for keyw ord_only values, none specified ' | 98 ('MakeComputedStyleBase requires an initial keyword for keyw ord_only values, none specified ' |
75 'for property ' + property['name']) | 99 'for property ' + property['name']) |
76 default_value = type_name + '::' + camel_case(property['initial_ keyword']) | 100 default_value = type_name + '::' + camel_case(property['initial_ keyword']) |
77 | 101 |
78 # If the property is independent, add the single-bit sized isInh erited flag | 102 # If the property is independent, add the single-bit sized isInh erited flag |
79 # to the list of member variable as well. | 103 # to the list of Fields as well. |
80 if property['independent']: | 104 if property['independent']: |
81 field_name_suffix_upper = property['upper_camel_name'] + 'Is Inherited' | 105 field_name_suffix_upper = property['upper_camel_name'] + 'Is Inherited' |
82 field_name_suffix_lower = property_name_lower + 'IsInherited ' | 106 field_name_suffix_lower = property_name_lower + 'IsInherited ' |
83 self._fields.append(Field( | 107 self._fields.append(Field( |
108 'inherited_flag', | |
84 name='m_' + field_name_suffix_lower, | 109 name='m_' + field_name_suffix_lower, |
85 property=property, | 110 property=property, |
86 is_enum=False, | |
87 is_inherited_flag=True, | |
88 type='bool', | 111 type='bool', |
89 size=1, | 112 size=1, |
90 default_value='true', | 113 default_value='true', |
91 getter_method_name=field_name_suffix_lower, | 114 getter_method_name=field_name_suffix_lower, |
92 setter_method_name='set' + field_name_suffix_upper, | 115 setter_method_name='set' + field_name_suffix_upper, |
93 initial_method_name='initial' + field_name_suffix_upper, | 116 initial_method_name='initial' + field_name_suffix_upper, |
94 resetter_method_name='reset' + field_name_suffix_upper, | 117 resetter_method_name='reset' + field_name_suffix_upper, |
95 is_inherited_method_name='', | |
96 )) | 118 )) |
97 | 119 |
98 # Add the property itself as a member variable. | 120 # Add the property itself as a member variable. |
99 self._fields.append(Field( | 121 self._fields.append(Field( |
122 'enum', | |
100 name=field_name, | 123 name=field_name, |
101 property=property, | 124 property=property, |
102 is_enum=True, | |
103 is_inherited_flag=False, | |
104 type=type_name, | 125 type=type_name, |
105 size=int(math.ceil(bits_needed)), | 126 size=int(math.ceil(bits_needed)), |
106 default_value=default_value, | 127 default_value=default_value, |
107 getter_method_name=property_name_lower, | 128 getter_method_name=property_name_lower, |
108 setter_method_name='set' + property_name, | 129 setter_method_name='set' + property_name, |
109 initial_method_name='initial' + property_name, | 130 initial_method_name='initial' + property_name, |
110 resetter_method_name='reset' + property_name, | 131 resetter_method_name='reset' + property_name, |
111 is_inherited_method_name=property_name_lower + 'IsInherited' , | 132 is_inherited_method_name=property_name_lower + 'IsInherited' , |
112 )) | 133 )) |
113 | 134 |
(...skipping 16 matching lines...) Expand all Loading... | |
130 @template_expander.use_jinja('ComputedStyleBaseConstants.h.tmpl') | 151 @template_expander.use_jinja('ComputedStyleBaseConstants.h.tmpl') |
131 def generate_base_computed_style_constants(self): | 152 def generate_base_computed_style_constants(self): |
132 return { | 153 return { |
133 'properties': self._properties, | 154 'properties': self._properties, |
134 'enums': self._computed_enums, | 155 'enums': self._computed_enums, |
135 'fields': self._fields, | 156 'fields': self._fields, |
136 } | 157 } |
137 | 158 |
138 if __name__ == '__main__': | 159 if __name__ == '__main__': |
139 in_generator.Maker(ComputedStyleBaseWriter).main(sys.argv) | 160 in_generator.Maker(ComputedStyleBaseWriter).main(sys.argv) |
OLD | NEW |