/[suikacvs]/messaging/manakai/lib/Message/DOM/ChangeLog
Suika

Diff of /messaging/manakai/lib/Message/DOM/ChangeLog

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.231 by wakaba, Sat Jul 7 07:36:58 2007 UTC revision 1.298 by wakaba, Fri Feb 8 15:08:04 2008 UTC
# Line 1  Line 1 
1    2008-02-08  Wakaba  <wakaba@suika.fam.cx>
2    
3            * CSSRule.pm (@media, @import ____new): Bless media object
4            with the appropriate class.
5            (@media css_text): Getter implemented.
6    
7            * MediaList.pm (media_text): Getter implemented.
8    
9    2008-02-03  Wakaba  <wakaba@suika.fam.cx>
10    
11            * CSSStyleDeclaration.pm ($serialize_value): Support
12            for new value types.
13    
14    2008-02-02  Wakaba  <wakaba@suika.fam.cx>
15    
16            * CSSStyleDeclaration.pm ($serialize_value): New (was
17            part of Whatpm::CSS::Parser as $default_serializer).
18            Use it instead of old 'serialize' parameter of CSS
19            property definition.
20    
21    2008-01-26  Wakaba  <wakaba@suika.fam.cx>
22    
23            * CSSStyleDeclaration.pm (css_text): Prepend | ! | before
24            the priority token if any.
25            (get_property_priority): Shorthand case implemented.
26    
27    2008-01-26  Wakaba  <wakaba@suika.fam.cx>
28    
29            * CSSStyleDeclaration.pm: Use |serialize_shorthand|
30            and |serialize_multiple| to serialize shorthand properties
31            in reflecting attributes.  Return value of
32            the |serialzie_multiple| function has been changed.
33            (non-computed css_text): Sort by property names.
34    
35    2008-01-24  Wakaba  <wakaba@suika.fam.cx>
36    
37            * Window.pm (manakai_get_computed_style): Renamed
38            from |get_computed_style|.
39    
40            * Element.pm (manakai_computed_style): Renamed from |current_style|.
41    
42    2008-01-14  Wakaba  <wakaba@suika.fam.cx>
43    
44            * CSSStyleDeclaration.pm (AUTOLOAD): DOM attributes reflecting
45            shorthand properties did croak (fixed but still they does not
46            return correct result - they need to be fixed later).
47    
48            * Element.pm (query_selector, query_selector_all): Prototypes
49            were missing.
50    
51    2008-01-14  Wakaba  <wakaba@suika.fam.cx>
52    
53            * Window.pm (___reset_css): Typo fixed.
54    
55    2008-01-14  Wakaba  <wakaba@suika.fam.cx>
56    
57            * CSSStyleDeclaration.pm: The classes now explicitly implement
58            the |CSS2Properties| interface.
59            (@{}, TIEARRAY, FETCH, FETCHSIZE, EXISTS, item, length): Implemented.
60    
61    2008-01-14  Wakaba  <wakaba@suika.fam.cx>
62    
63            * CSSStyleDeclaration.pm (attributes reflecting CSS properties):
64            Return an empty string if no value is assigned to the property.  Insert
65            a SPACE before '!' for compatibility with Firefox.
66    
67    2008-01-14  Wakaba  <wakaba@suika.fam.cx>
68    
69            * CSSRule.pm (css_text): Trailing newline character is removed
70            to avoid double empty lines in CSSStyleSheet->css_text.
71            (selector_text): Namespace support is fixed.
72    
73            * CSSStyleSheet.pm (___new): Now it accepts |_nsmap| option.
74    
75    2008-01-14  Wakaba  <wakaba@suika.fam.cx>
76    
77            * CSSRule.pm (selector_text): Use |serialize_selector_text|
78            to get better result.
79    
80    2008-01-13  Wakaba  <wakaba@suika.fam.cx>
81    
82            * Window.pm: New Perl module.
83    
84            * Document.pm (default_view): Implemented.
85    
86            * Element.pm (current_style): Implemented.
87    
88    2008-01-06  Wakaba  <wakaba@suika.fam.cx>
89    
90            * CSSStyleDeclaration.pm (css_text): Allow to shorten a complete
91            set of longhand properties.
92            (get_property_priority): Implemented.
93            (CSSComputedStyleDeclaration AUTOLOAD): Implemented for reflecting
94            attributes.
95    
96    2008-01-04  Wakaba  <wakaba@suika.fam.cx>
97    
98            * CSSStyleDeclaration.pm (css_text): Allow |{compute_multiple}|
99            as well as |{compute}| as a way to filter out longhand
100            properties.  Sort properties by names for readability.
101    
102    2008-01-01  Wakaba  <wakaba@suika.fam.cx>
103    
104            * CSSStyleDeclaration.pm (css_text): Output |undef| property
105            information for debugging.
106    
107            * CSSStyleSheet.pm (manakai_base_uri): New attribute.
108    
109    2008-01-01  Wakaba  <wakaba@suika.fam.cx>
110    
111            * CSSStyleDeclaration.pm (CSSComputedStyleDeclaration): New class.
112    
113    2007-12-31  Wakaba  <wakaba@suika.fam.cx>
114    
115            * SelectorsAPI.pm, Document.pm (___query_selector_all): New internal
116            method.
117    
118    2007-12-31  Wakaba  <wakaba@suika.fam.cx>
119    
120            * SelectorsAPI.pm: Make simple-selector-sequence-matching
121            an independent function.
122    
123    2007-12-31  Wakaba  <wakaba@suika.fam.cx>
124    
125            * CSSStyleDeclaration.pm (AUTOLOAD): Getter for attributes
126            reflecting CSS property is implemented.
127            (css_text): Getter is implemented.
128    
129    2007-12-24  Wakaba  <wakaba@suika.fam.cx>
130    
131            * CSSRule.pm (selector_text): Ad hoc support for namespace prefixes.
132            (CSSNamespaceRule.css_text): Getter implemented.
133    
134            * CSSStyleSheet.pm (manakai_is_default_namespace,
135            manakai_lookup_namespace_prefix): New methods.
136    
137    2007-12-23  Wakaba  <wakaba@suika.fam.cx>
138    
139            * CSSRule.pm (@charset.css_text): Implemented.
140    
141    2007-12-23  Wakaba  <wakaba@suika.fam.cx>
142    
143            * CSSRule.pm (type, css_text): Typo fixed.
144            (____new): s/_selector/_selectors/g;
145            (CSSStyleRule.css_text, selectors_text): Ad hoc implementation.
146    
147            * CSSStyleDeclaration.pm (css_text): Ad hoc implementation.
148    
149            * CSSStyleSheet.pm (new): s/new/____new/.
150            (css_text): New attribute.
151    
152    2007-12-22  Wakaba  <wakaba@suika.fam.cx>
153    
154            * MediaList.pm: New placeholder for a CSSOM interface.
155    
156            * CSSRule.pm, CSSStyleSheet.pm: Implementing the initial
157            setting of owner* and parent* attributes; support
158            for the |delete_rule| method.
159    
160    2007-12-22  Wakaba  <wakaba@suika.fam.cx>
161    
162            * CSSStyleSheet.pm, CSSRule.pm, CSSRuleList.pm, CSSStyleDeclaration.pm:
163            First version of CSSOM implementation.
164    
165    2007-11-18  Wakaba  <wakaba@suika.fam.cx>
166    
167            * Document.pm, Entity.pm (manakai_has_bom,
168            manakai_charset): New attributes.
169    
170    2007-11-11  Wakaba  <wakaba@suika.fam.cx>
171    
172            * Document.pm, Element.pm (inner_html): Use |Whatpm::HTML::Serializer|
173            for getter.
174    
175    2007-10-27  Wakaba  <wakaba@suika.fam.cx>
176    
177            * Event.pm (init_event, init_event_ns, init_custom_event_ns):
178            The |namespaceURI| attribute was not set correctly.
179    
180            * DOMEvents.dis: Removed.
181    
182    2007-10-08  Wakaba  <wakaba@suika.fam.cx>
183    
184            * Event.pm, EventTarget.pm, EventTargetNode.pm,
185            EventException.pm: Implemented (but not tested!).
186    
187            * DOMException.pm (MALFORMED_EVENT_TYPE_ERR,
188            EVENT_INTERFACE_NOT_SUPPORTED_ERR, EXTERNAL_EVENT_ERR): New
189            error subtypes.
190    
191            * DOMImplementation.pm ($HasFeature): The |Event| feature,
192            version |3.0|, is added.
193    
194            * Document.pm, Node.pm: Event attributes and
195            methods are implemented.
196    
197    2007-10-07  Wakaba  <wakaba@suika.fam.cx>
198    
199            * SelectorsAPI.pm ($get_elements_by_selectors): Receive
200            an additional argument for "current element".
201            Support for |-manakai-current| and |-manakai-current(/s/)|
202            pseudo-classes.
203    
204    2007-09-29  Wakaba  <wakaba@suika.fam.cx>
205    
206            * SelectorsAPI.pm: Attribute selectors are implemented.
207    
208    2007-09-29  Wakaba  <wakaba@suika.fam.cx>
209    
210            * SelectorsAPI.pm (ElementSelector): Implemented.
211    
212    2007-09-29  Wakaba  <wakaba@suika.fam.cx>
213    
214            * SelectorsAPI.pm (query_selector): Implemented.
215    
216    2007-09-29  Wakaba  <wakaba@suika.fam.cx>
217    
218            * SelectorsAPI.pm ($get_elements_by_selectors): Created
219            from most part of |query_selector_all|.
220    
221    2007-09-24  Wakaba  <wakaba@suika.fam.cx>
222    
223            * DOMException.pm (SYNTAX_ERR): New subtype is defined.
224            (UNDECLARED_PREFIX_ERR): New subtype is defined.
225    
226            * Document.pm (Document): Implements the |DocumentSelector|
227            interface.
228    
229            * Element.pm (Element): Implements the |ElementSelector|
230            interface.
231    
232            * Node.pm (Node): Implements the |NSResolver| interface.
233    
234            * SelectorsAPI.pm: Now (hopefully) conform to the Selectors
235            API Editor's Draft (only |query_selector_all| on |Document|,
236            with limited selectors syntax support, though).
237    
238    2007-09-23  Wakaba  <wakaba@suika.fam.cx>
239    
240            * SelectorsAPI.pm: Namespaced type/universal selectors
241            are supported.
242    
243    2007-09-23  Wakaba  <wakaba@suika.fam.cx>
244    
245            * SelectorsAPI.pm: New Perl module.
246    
247    2007-08-25  Wakaba  <wakaba@suika.fam.cx>
248    
249            * Node.pm (manakai_language): Return the |manakai_language|
250            of the |owner_document|, if any, as defined in the spec.
251    
252    2007-08-25  Wakaba  <wakaba@suika.fam.cx>
253    
254            * Makefile: Relative path was wrong.
255    
256    2007-07-29  Wakaba  <wakaba@suika.fam.cx>
257    
258            * HTML/: New directory.
259    
260            * Element.pm (create_element_ns): Return object implementing
261            the |HTMLElement| interface for HTML elements.
262    
263    2007-07-29  Wakaba  <wakaba@suika.fam.cx>
264    
265            * DOMImplementation.pod: New documentation.
266    
267            * Makefile: Make HTML document.
268    
269    2007-07-29  Wakaba  <wakaba@suika.fam.cx>
270    
271            * XDoctype.dis, XDoctype.pm: Removed.
272    
273            * CharacterData.pm: Renamed from DOMCharacterData.pm.
274    
275            * Document.pm: Renamed from DOMDocument.pm.
276    
277            * Element.pm: Renamed from DOMElement.pm
278    
279    2007-07-29  Wakaba  <wakaba@suika.fam.cx>
280    
281            * DOMString.dis, DOMString.pm, Document.dis, Document.pm,
282            Element.dis, Element.pm, CharacterData.dis, CharacterData.pm,
283            TreeCore.dis, TreeCore.pm, DOMCore.dis, DOMCore.pm,
284            DOMFeature.dis, DOMFeature.pm, XML.dis, XML.pm,
285            DOMMain.dis, DOMMain.pm, DOMLS.dis,
286            GenericLS.dis, GenericLS.pm, SimpleLS.dis: Removed.
287    
288            * Makefile: Rules for DIS are removed.
289    
290    2007-07-29  Wakaba  <wakaba@suika.fam.cx>
291    
292            * Text.pm: |Message::DOM::Traversal, an obsolete module,
293            was referenced.
294    
295    2007-07-29  Wakaba  <wakaba@suika.fam.cx>
296    
297            * DOMDocument.pm (inner_html): Setter in HTML document
298            is implemented.
299    
300    2007-07-29  Wakaba  <wakaba@suika.fam.cx>
301    
302            * DOMDocument.pm (inner_html): Setter in XML document
303            is implemented.
304    
305    2007-07-19  Wakaba  <wakaba@suika.fam.cx>
306    
307            * Attr.pm (DeclaredValueType): Added.
308    
309            * ProcessingInstruction.pm (data): Accept |undef|
310            as a valid input, for |text_content| (maybe) allows it.
311    
312            * TypeInfo.pm (type_namespace): The implementation was wrong.
313    
314    2007-07-16  Wakaba  <wakaba@suika.fam.cx>
315    
316            * DOMElement.pm: Incorrect module was referenced.
317    
318            * DOMImplementation.pm: References to
319            the |Message::Charset::Encode| module has been removed.
320    
321    2007-07-15  Wakaba  <wakaba@suika.fam.cx>
322    
323            * XMLParserTemp.pm: Use |Whatpm::Charset::DecodeHandle|
324            instead of |Message::Charset::Encode|.
325    
326    2007-07-15  Wakaba  <wakaba@suika.fam.cx>
327    
328            * DOMDocument.pm (inner_html): New attribute (beta).
329    
330            * DOMElement.pm (inner_html): New attribute (beta).
331    
332    2007-07-15  Wakaba  <wakaba@suika.fam.cx>
333    
334            * DOMConfiguration.pm: Configuration parameter |create-child-element|
335            implemented.
336    
337            * DOMElement.pm (create_element_ns): Support for Atom
338            subclasses.
339    
340            * DOMImplementation.pm (DOMImplementation): Now
341            implements the |AtomDOMImplementation| interface.
342            ($HasFeature): Features |atom| and |atomthreading| are added.
343    
344            * NodeList.pm (StaticNodeList): Implemented.
345    
346    2007-07-15  Wakaba  <wakaba@suika.fam.cx>
347    
348            * Atom/: New directory.
349    
350    2007-07-15  Wakaba  <wakaba@suika.fam.cx>
351    
352            * TreeWalker.pm, SerialWalker.pm: New Perl modules.
353    
354            * Text.pm (whole_text): Parameter index number has
355            been changed to support new |NodeFilter| Perl binding
356            definition.
357    
358    2007-07-14  Wakaba  <wakaba@suika.fam.cx>
359    
360            * AttributeDefinition.pm, DOMElement.pm, DocumentType.pm,
361            ElementTypeDefinition.pm, Entity.pm, EntityReference.pm,
362            Notation.pm, ProcessingInstruction.pm (AUTOLOAD): Don't croak even if an attempt is made to modify a read-only attribute.
363    
364            * DOMConfiguration.pm (can_set_parameter,
365            set_parameter): Don't allow to set the value
366            to a string other than <http://www.w3.org/TR/REC-xml> (XML 1.0 DTD).
367    
368            * DOMDocument.pm (Message::IF::DocumentTraversal): New interface.
369            (create_tree_walker, manakai_create_serial_walker): References
370            and prototypes are added.
371    
372            * DOMException.pm (NULLPO_ERR): New error type:-).
373    
374            * DOMImplementation.pm ($HasFeature): Feature |Traversal|,
375            version |2.0|, is added.
376    
377    2007-07-14  Wakaba  <wakaba@suika.fam.cx>
378    
379            * CDATASection.pm: Removed (merged with |Text.pm|).
380    
381            * Text.pm (Message::DOM::Text::CDATASection): New.
382    
383            * Comment.pm: Removed (merged with |DOMCharacterData.pm|).
384    
385            * DOMCharacterData.pm (Message::DOM::CharacterData::Comment): New.
386    
387    2007-07-14  Wakaba  <wakaba@suika.fam.cx>
388    
389            * DOMConfiguration.pm: Support for |schema-type|
390            and |http://suika.fam.cx/www/2006/dom-config/xml-id|.
391    
392            * NamedNodeMap (TIEHASH): Were missing.
393    
394    2007-07-14  Wakaba  <wakaba@suika.fam.cx>
395    
396            * AttributeDefinition.pm (node_value): Implemented.
397            (create_attribute_definition): Implemented.
398    
399            * DOMConfiguration.pm (%{}, TIEHASH,
400            get_parameter, set_parameter, can_set_parameter,
401            EXISTS, DELETE, parameter_names, FETCH, STORE,
402            FIRSTKEY, LASTKEY): Implemented.
403    
404            * DOMDocument.pm (____new): Set |error-handler| default.
405            (get_elements_by_tag_name, get_elements_by_tag_name_ns): Implemented.
406    
407            * DOMElement.pm (get_elements_by_tag_name, get_elements_by_tag_name_ns):
408            Implemented.
409    
410            * DOMException.pm: Error types for |DOMConfiguration|
411            are added.
412    
413            * DOMStringList.pm (Message::DOM::DOMStringList::StaticList): New
414            class.
415    
416            * DocumentType.pm (get_element_type_definition_node,
417            get_general_entity_node, get_notation_node,
418            set_element_type_definition_node, set_general_entity_node,
419            set_notation_node, create_document_type_definition): Implemented.
420    
421            * ElementTypeDefinition.pm (get_attribute_definition_node,
422            set_attribute_definition_node, create_element_type_definition):
423            Implemented.
424    
425            * Entity.pm (create_general_entity): Implemented.
426    
427            * Node.pm: Constants in |OperationType| definition
428            group are added.
429            (manakai_language): Implemented.
430    
431            * NodeList.pm (Message::DOM::NodeList::GetElementsList): New
432            class.
433    
434            * Notation.pm (create_notation): Implemented.
435    
436    2007-07-14  Wakaba  <wakaba@suika.fam.cx>
437    
438            * TypeInfo.pm: New Perl module.
439    
440            * Attr.pm: Use |manakai_local_name| rather than |local_name|
441            to avoid HTML5 case normalization.
442            (is_id): Implemented.
443            (manakai_name): New attribute.
444            (schema_type_info): Implemented.
445            (create_attribute_ns): Empty string as namespace URI
446            was not supported.
447    
448            * DOMElement.pm (clone_node): Removed since now it is
449            defined in |Node.pm|.
450            (schema_type_info): Implemented.
451            (manakai_tag_name): New attribute.
452            (get_attribute, get_attribute_node, get_attribute_ns,
453            get_attribute_node_ns, has_attribute, has_attribute_ns,
454            remove_attribute, remove_attribute_ns,
455            remove_attribute_node, set_attribute, set_attribute_ns,
456            set_id_attribute, set_id_attribute_node,
457            set_id_attribute_ns): Implemented.
458            (create_element_ns): Empty string as namespace URI
459            was not supported.
460    
461    2007-07-12  Wakaba  <wakaba@suika.fam.cx>
462    
463            * AttributeDefinition.pm (owner_element_type_definition): Implemented.
464    
465            * DocumentType.pm (create_document_type_definition): Initialize
466            |public_id|, |system_id|, and |internal_subset| attributes
467            by empty strings for compatibility with Web browsers.
468            (create_document_type): Initialize |internal_subset|
469            attribute by an empty string for compatibility with
470            Web browsers.
471    
472            * ElementTypeDefinition.pm, Entity.pm,
473            Notation.pm (owner_document_type_definition): Implemented.
474    
475    2007-07-08  Wakaba  <wakaba@suika.fam.cx>
476    
477            * DOMImplementation.pm ($HasFeature): |fe:XDoctypeDeclaration|
478            feature is added for compatibility with |XMLParserTemp.pm|.
479    
480    2007-07-08  Wakaba  <wakaba@suika.fam.cx>
481    
482            * Attr.pm (value, node_value): Now it is defined
483            as |text_content| itself.
484    
485            * AttributeDefinition.pm, ElementTypeDefinition.pm,
486            Node.pm (AUTOLOAD): Unused block is removed.
487    
488            * CDATASection.pm, DocumentFragment.pm (AUTOLOAD): Removed.  Unused.
489    
490            * DocumentType.pm (internal_subset): Implemented.
491    
492            * Entity.pm (is_externally_declared, input_encoding,
493            xml_version): Implemented.
494    
495            * ProcessingInstruction.pm (target, data): Implemented.
496    
497    2007-07-08  Wakaba  <wakaba@suika.fam.cx>
498    
499            * DOMCharacterData.pm (AUTOLOAD): Removed.
500            (data): Reimplemented.
501            (delete_data, insert_data, replace_data, substring_data): There were
502            a number of bugs.
503    
504            * Text.pm (AUTOLOAD): Removed.  Unused.
505    
506    2007-07-08  Wakaba  <wakaba@suika.fam.cx>
507    
508            * StringExtended.pm: New Perl module.
509    
510            * DOMCharacterData.pm (length, append_data, delete_data,
511            insert_data, replace_data, substring_data): Implemented.
512    
513            * DOMException.pm (INDEX_SIZE_ERR): Implemented.
514    
515            * Text.pm (is_element_content_whitespace, whole_text,
516            split_text): Implemented.
517    
518    2007-07-08  Wakaba  <wakaba@suika.fam.cx>
519    
520            * DOMElement.pm (attributes): Implemented.
521    
522            * DOMException.pm (INUSE_DEFINITION_ERR): New error type.
523    
524            * DocumentType.pm (entities, general_entities,
525            notations, element_types): Implemented.
526    
527            * ElementTypeDefinition.pm (attribute_definitions): Implemented.
528    
529            * NamedNodeMap.pm: New Perl module.
530    
531    2007-07-08  Wakaba  <wakaba@suika.fam.cx>
532    
533            * Attr.pm, AttributeDefinition.pm, DOMCharacterData.pm,
534            DOMDocument.pm, DocumentType.pm, ElementTypeDefinition.pm,
535            Node.pm, Notation.pm, ProcessingInstruction.pm (append_child,
536            insert_before, replace_child): Implemented.
537    
538            * DOMException.pm (HIERARCHY_REQUEST_ERR, NOT_FOUND_ERR): Implemented.
539    
540            * Node.pm (remove_child): Implemented.
541    
542    2007-07-07  Wakaba  <wakaba@suika.fam.cx>
543    
544            * Node.pm (==, is_equal_node): Implemented.
545            (is_same_node): Implemented.
546            (get_feature, get_user_data, set_user_data): Implemented.
547            (is_supported): Implemented.
548            
549    2007-07-07  Wakaba  <wakaba@suika.fam.cx>
550    
551            * DOMDocument.pm (get_element_by_id): Implemented.
552            (create_document): Implemented.
553    
554            * DOMException.pm (EXTERNAL_OBJECT_ERR, INUSE_DOCTYPE_ERR): New
555            errors.
556            (QNAME_NULLNS_ERR): New errors.
557    
558            * DocumenType.pm (create_document_type): Implemented.
559    
560    2007-07-07  Wakaba  <wakaba@suika.fam.cx>
561    
562            * CDATASection.pm (is_element_content_whitespace): New.
563    
564            * DOMElement.pm (has_attribute): Alpha version.
565            (create_element, create_element_ns): Implemented.
566    
567            * DocumentType.pm (get_general_entity_node): Alpha version.
568    
569            * EntityReference.pm (create_entity_reference): Implemented.
570    
571            * ProcessingInstruction.pm (create_processing_instruction): Implemented.
572    
573    2007-07-07  Wakaba  <wakaba@suika.fam.cx>
574    
575            * Attr.pm (create_attribute, create_attribute_ns): Implemented.
576    
577            * DOMDocument.pm: Load character classes from |Char::Class::XML|.
578            (compat_mode): Check |defined| not to be warned as "uninitialized"
579            when |{manakai_compat_mode}| is |undef|.
580    
581            * DOMException.pm (INVALID_CHARACTER_ERR, NAMESPACE_ERR): Added.
582    
583            * DOMImplementationRegistry.pm, DOMImplementationSource.pm:
584            Statements to set |$Error::Depth| are removed since they
585            are result in "uninitialized" warnings unless
586            the |Message::DOM::DOMException| module is loaded earlier.
587            Usually methods invoked in these methods does not
588            raise any exception so that it makes no difference.
589    
590  2007-07-07  Wakaba  <wakaba@suika.fam.cx>  2007-07-07  Wakaba  <wakaba@suika.fam.cx>
591    
592          * DOMDocument.pm (adopt_node): Implemented.          * DOMDocument.pm (adopt_node): Implemented.

Legend:
Removed from v.1.231  
changed lines
  Added in v.1.298

admin@suikawiki.org
ViewVC Help
Powered by ViewVC 1.1.24