Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Loading…

Merging and cleanup of existing branches #16

Open
wants to merge 21 commits into from

5 participants

@JanX2

These commits add ARC compatibility while retaining backwards compatibility with non-ARC targets. They also merge in some of the features found in other forks and are an attempt to clean everything.

/cc @tijoinc, @tresni, @tuoxie007, @flipstudio, @floorjiann, @aidann, @VegetarianZombie, @bamse16, @neocoin, @spawrks, @AhnSeongHyun, @larsw

@tresni tresni referenced this pull request
Closed

innerHTML + ARC #14

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on Jun 21, 2011
  1. @neocoin
  2. @neocoin
  3. @neocoin

    solved conflict

    neocoin authored
Commits on Aug 31, 2011
  1. @gvieira

    HTMLNode new features

    gvieira authored
Commits on Sep 8, 2011
  1. @pietrocaselani
Commits on Dec 1, 2011
  1. @pietrocaselani
Commits on Nov 27, 2012
  1. Reformatting long method selectors.

    Jan Weiß authored
  2. Cleanup.

    Jan Weiß authored
  3. Fixing leak.

    Jan Weiß authored
  4. ARCifying.

    Jan Weiß authored
  5. Merge remote-tracking branch 'refs/remotes/flipstudio/master'

    Jan Weiß authored
    Conflicts:
    	HTMLNode.m
  6. ARCifying.

    Jan Weiß authored
  7. @aidanns

    Added license with best guess of MIT. Sourced from zootreeves#8

    aidanns authored Jan Weiß committed
  8. Updating LICENSE.

    Jan Weiß authored
  9. Fixing indentation.

    Jan Weiß authored
  10. Adding “example.m”.

    Jan Weiß authored
  11. Renaming “-findChildTags:” to “-findChildrenWithTag:” and “-findChild…

    Jan Weiß authored
    …Tag:” to “-findChildWithTag:”, deprecating old methods.
    
    This is based on work by @tijoinc (Tim Johnsen):
    tijoinc@a291ce1
  12. Cleanup.

    Jan Weiß authored
This page is out of date. Refresh to see the latest.
View
39 HTMLNode.h
@@ -33,7 +33,7 @@ typedef enum
HTMLBlockQuoteNode,
} HTMLNodeType;
-@interface HTMLNode : NSObject
+@interface HTMLNode : NSObject <NSCopying>
{
@public
xmlNode * _node;
@@ -43,6 +43,8 @@ typedef enum
//Use [parser doc] to get the root Node
-(id)initWithXMLNode:(xmlNode*)xmlNode;
++(id)nodeWithName:(NSString *)name;
+
//Returns a single child of class
-(HTMLNode*)findChildOfClass:(NSString*)className;
@@ -52,19 +54,33 @@ typedef enum
//Finds a single child with a matching attribute
//set allowPartial to match partial matches
//e.g. <img src="http://www.google.com> [findChildWithAttribute:@"src" matchingName:"google.com" allowPartial:TRUE]
--(HTMLNode*)findChildWithAttribute:(NSString*)attribute matchingName:(NSString*)className allowPartial:(BOOL)partial;
+-(HTMLNode*)findChildWithAttribute:(NSString*)attribute
+ matchingName:(NSString*)className
+ allowPartial:(BOOL)partial;
//Finds all children with a matching attribute
--(NSArray*)findChildrenWithAttribute:(NSString*)attribute matchingName:(NSString*)className allowPartial:(BOOL)partial;
+-(NSArray*)findChildrenWithAttribute:(NSString*)attribute
+ matchingName:(NSString*)className
+ allowPartial:(BOOL)partial;
+
+-(NSArray*)nodesForXPath:(NSString*)xpath;
//Gets the attribute value matching tha name
-(NSString*)getAttributeNamed:(NSString*)name;
-//Find childer with the specified tag name
--(NSArray*)findChildTags:(NSString*)tagName;
+-(void)setAttributeNamed:(NSString *)name withValue:(NSString *)value;
+
+-(void)addAttributeNamed:(NSString *)name withValue:(NSString *)value;
+
+-(void)removeAttributeNamed:(NSString *)name;
+
+//Find children with the specified tag name
+-(NSArray*)findChildrenWithTag:(NSString*)tagName;
+-(NSArray*)findChildTags:(NSString*)tagName DEPRECATED_ATTRIBUTE;
//Looks for a tag name e.g. "h3"
--(HTMLNode*)findChildTag:(NSString*)tagName;
+-(HTMLNode*)findChildWithTag:(NSString*)tagName;
+-(HTMLNode*)findChildTag:(NSString*)tagName DEPRECATED_ATTRIBUTE;
//Returns the first child element
-(HTMLNode*)firstChild;
@@ -78,6 +94,9 @@ typedef enum
//Returns the html contents of the node
-(NSString*)rawContents;
+//Returns rawContents - surrounding tag
+-(NSString*)innerHTML;
+
//Returns next sibling in tree
-(HTMLNode*)nextSibling;
@@ -107,5 +126,13 @@ HTMLNodeType nodeType(xmlNode* node);
NSString * allNodeContents(xmlNode*node);
NSString * rawContentsOfNode(xmlNode * node);
+#pragma mark - Flip Studio mods
+
+- (NSArray *)childrenForXPath:(NSString *)xpath;
+- (void)setContent:(NSString *)content;
+- (void)addNextSibling:(HTMLNode *)child;
+- (void)addPrevSibling:(HTMLNode *)child;
+- (void)addChild:(HTMLNode *)child;
+- (void)removeFromParent;
@end
View
318 HTMLNode.m
@@ -8,31 +8,36 @@
#import "HTMLNode.h"
#import <libxml/HTMLtree.h>
+#import <libxml/xpath.h>
+#import <libxml/xpathInternals.h>
+
+
+#import "JXArcCompatibilityMacros.h"
@implementation HTMLNode
-(HTMLNode*)parent
{
- return [[[HTMLNode alloc] initWithXMLNode:_node->parent] autorelease];
+ return JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:_node->parent]);
}
-(HTMLNode*)nextSibling {
- return [[[HTMLNode alloc] initWithXMLNode:_node->next] autorelease];
+ return JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:_node->next]);
}
-(HTMLNode*)previousSibling {
- return [[[HTMLNode alloc] initWithXMLNode:_node->prev] autorelease];
+ return JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:_node->prev]);
}
void setAttributeNamed(xmlNode * node, const char * nameStr, const char * value) {
char * newVal = (char *)malloc(strlen(value)+1);
- memcpy (newVal, value, strlen(value)+1);
-
+ memcpy(newVal, value, strlen(value)+1);
+
for(xmlAttrPtr attr = node->properties; NULL != attr; attr = attr->next)
{
if (strcmp((char*)attr->name, nameStr) == 0)
- {
+ {
for(xmlNode * child = attr->children; NULL != child; child = child->next)
{
free(child->content);
@@ -43,7 +48,7 @@ void setAttributeNamed(xmlNode * node, const char * nameStr, const char * value)
}
}
-
+ free(newVal);
}
NSString * getAttributeNamed(xmlNode * node, const char * nameStr)
@@ -51,7 +56,7 @@ void setAttributeNamed(xmlNode * node, const char * nameStr, const char * value)
for(xmlAttrPtr attr = node->properties; NULL != attr; attr = attr->next)
{
if (strcmp((char*)attr->name, nameStr) == 0)
- {
+ {
for(xmlNode * child = attr->children; NULL != child; child = child->next)
{
return [NSString stringWithCString:(void*)child->content encoding:NSUTF8StringEncoding];
@@ -65,7 +70,7 @@ void setAttributeNamed(xmlNode * node, const char * nameStr, const char * value)
}
-(NSString*)getAttributeNamed:(NSString*)name
-{
+{
const char * nameStr = [name UTF8String];
return getAttributeNamed(_node, nameStr);
@@ -86,23 +91,27 @@ -(NSString*)tagName
-(HTMLNode*)firstChild
{
- return [[[HTMLNode alloc] initWithXMLNode:_node->children] autorelease];
+ return JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:_node->children]);
}
--(void)findChildrenWithAttribute:(const char*)attribute matchingName:(const char*)className inXMLNode:(xmlNode *)node inArray:(NSMutableArray*)array allowPartial:(BOOL)partial
+-(void)findChildrenWithAttribute:(const char*)attribute
+ matchingName:(const char*)className
+ inXMLNode:(xmlNode *)node
+ inArray:(NSMutableArray*)array
+ allowPartial:(BOOL)partial
{
xmlNode *cur_node = NULL;
const char * classNameStr = className;
//BOOL found = NO;
- for (cur_node = node; cur_node; cur_node = cur_node->next)
- {
+ for (cur_node = node; cur_node; cur_node = cur_node->next)
+ {
for(xmlAttrPtr attr = cur_node->properties; NULL != attr; attr = attr->next)
{
if (strcmp((char*)attr->name, attribute) == 0)
- {
+ {
for(xmlNode * child = attr->children; NULL != child; child = child->next)
{
@@ -111,11 +120,11 @@ -(void)findChildrenWithAttribute:(const char*)attribute matchingName:(const char
match = YES;
else if (partial && strstr ((char*)child->content, classNameStr) != NULL)
match = YES;
-
+
if (match)
{
//Found node
- HTMLNode * nNode = [[[HTMLNode alloc] initWithXMLNode:cur_node] autorelease];
+ HTMLNode * nNode = JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:cur_node]);
[array addObject:nNode];
break;
}
@@ -125,84 +134,97 @@ -(void)findChildrenWithAttribute:(const char*)attribute matchingName:(const char
}
[self findChildrenWithAttribute:attribute matchingName:className inXMLNode:cur_node->children inArray:array allowPartial:partial];
- }
+ }
}
--(void)findChildTags:(NSString*)tagName inXMLNode:(xmlNode *)node inArray:(NSMutableArray*)array
+-(void)findChildrenWithTag:(NSString*)tagName
+ inXMLNode:(xmlNode *)node
+ addingToArray:(NSMutableArray*)array
{
xmlNode *cur_node = NULL;
- const char * tagNameStr = [tagName UTF8String];
+ const char * tagNameStr = [tagName UTF8String];
if (tagNameStr == nil)
return;
- for (cur_node = node; cur_node; cur_node = cur_node->next)
- {
+ for (cur_node = node; cur_node; cur_node = cur_node->next)
+ {
if (cur_node->name && strcmp((char*)cur_node->name, tagNameStr) == 0)
{
- HTMLNode * node = [[[HTMLNode alloc] initWithXMLNode:cur_node] autorelease];
+ HTMLNode * node = JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:cur_node]);
[array addObject:node];
}
- [self findChildTags:tagName inXMLNode:cur_node->children inArray:array];
- }
+ [self findChildrenWithTag:tagName inXMLNode:cur_node->children addingToArray:array];
+ }
}
--(NSArray*)findChildTags:(NSString*)tagName
+-(NSArray*)findChildrenWithTag:(NSString*)tagName
{
NSMutableArray * array = [NSMutableArray array];
- [self findChildTags:tagName inXMLNode:_node->children inArray:array];
+ [self findChildrenWithTag:tagName inXMLNode:_node->children addingToArray:array];
return array;
}
--(HTMLNode*)findChildTag:(NSString*)tagName inXMLNode:(xmlNode *)node
+-(NSArray*)findChildTags:(NSString*)tagName
+{
+ return [self findChildrenWithTag:tagName];
+}
+
+
+-(HTMLNode*)findChildWithTag:(NSString*)tagName
+ inXMLNode:(xmlNode *)node
{
xmlNode *cur_node = NULL;
- const char * tagNameStr = [tagName UTF8String];
+ const char * tagNameStr = [tagName UTF8String];
- for (cur_node = node; cur_node; cur_node = cur_node->next)
- {
+ for (cur_node = node; cur_node; cur_node = cur_node->next)
+ {
if (cur_node && cur_node->name && strcmp((char*)cur_node->name, tagNameStr) == 0)
{
- return [[[HTMLNode alloc] initWithXMLNode:cur_node] autorelease];
+ return JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:cur_node]);
}
- HTMLNode * cNode = [self findChildTag:tagName inXMLNode:cur_node->children];
+ HTMLNode * cNode = [self findChildWithTag:tagName inXMLNode:cur_node->children];
if (cNode != NULL)
{
return cNode;
}
- }
+ }
return NULL;
}
--(HTMLNode*)findChildTag:(NSString*)tagName
+-(HTMLNode*)findChildWithTag:(NSString*)tagName
{
- return [self findChildTag:tagName inXMLNode:_node->children];
+ return [self findChildWithTag:tagName inXMLNode:_node->children];
}
+-(HTMLNode*)findChildTag:(NSString*)tagName;
+{
+ return [self findChildWithTag:tagName];
+}
-(NSArray*)children
{
xmlNode *cur_node = NULL;
- NSMutableArray * array = [NSMutableArray array];
-
- for (cur_node = _node->children; cur_node; cur_node = cur_node->next)
- {
- HTMLNode * node = [[[HTMLNode alloc] initWithXMLNode:cur_node] autorelease];
+ NSMutableArray * array = [NSMutableArray array];
+
+ for (cur_node = _node->children; cur_node; cur_node = cur_node->next)
+ {
+ HTMLNode * node = JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:cur_node]);
[array addObject:node];
}
return array;
}
-/*
+#if 0
-(NSString*)description
{
NSString * string = [NSString stringWithFormat:@"<%s>%@\n", _node->name, [self contents]];
@@ -213,25 +235,29 @@ -(NSString*)description
}
string = [string stringByAppendingString:[NSString stringWithFormat:@"<%s>\n", _node->name]];
-
+
return string;
-}*/
+}
+#endif
--(HTMLNode*)findChildWithAttribute:(const char*)attribute matchingName:(const char*)name inXMLNode:(xmlNode *)node allowPartial:(BOOL)partial
+-(HTMLNode*)findChildWithAttribute:(const char*)attribute
+ matchingName:(const char*)name
+ inXMLNode:(xmlNode *)node
+ allowPartial:(BOOL)partial
{
xmlNode *cur_node = NULL;
const char * classNameStr = name;
//BOOL found = NO;
-
+
if (node == NULL)
return NULL;
- for (cur_node = node; cur_node; cur_node = cur_node->next)
- {
+ for (cur_node = node; cur_node; cur_node = cur_node->next)
+ {
for(xmlAttrPtr attr = cur_node->properties; NULL != attr; attr = attr->next)
- {
+ {
if (strcmp((char*)attr->name, attribute) == 0)
- {
+ {
for(xmlNode * child = attr->children; NULL != child; child = child->next)
{
@@ -242,8 +268,8 @@ -(HTMLNode*)findChildWithAttribute:(const char*)attribute matchingName:(const ch
match = YES;
if (match)
- {
- return [[[HTMLNode alloc] initWithXMLNode:cur_node] autorelease];
+ {
+ return JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:cur_node]);
}
}
break;
@@ -255,26 +281,30 @@ -(HTMLNode*)findChildWithAttribute:(const char*)attribute matchingName:(const ch
{
return cNode;
}
- }
-
+ }
+
return NULL;
}
--(HTMLNode*)findChildWithAttribute:(NSString*)attribute matchingName:(NSString*)className allowPartial:(BOOL)partial
+-(HTMLNode*)findChildWithAttribute:(NSString*)attribute
+ matchingName:(NSString*)className
+ allowPartial:(BOOL)partial
{
return [self findChildWithAttribute:[attribute UTF8String] matchingName:[className UTF8String] inXMLNode:_node->children allowPartial:partial];
}
-(HTMLNode*)findChildOfClass:(NSString*)className
-{
- HTMLNode * node = [self findChildWithAttribute:"class" matchingName:[className UTF8String] inXMLNode:_node->children allowPartial:NO];
+{
+ HTMLNode * node = [self findChildWithAttribute:"class" matchingName:[className UTF8String] inXMLNode:_node->children allowPartial:NO];
return node;
}
--(NSArray*)findChildrenWithAttribute:(NSString*)attribute matchingName:(NSString*)className allowPartial:(BOOL)partial
+-(NSArray*)findChildrenWithAttribute:(NSString*)attribute
+ matchingName:(NSString*)className
+ allowPartial:(BOOL)partial
{
NSMutableArray * array = [NSMutableArray array];
-
+
[self findChildrenWithAttribute:[attribute UTF8String] matchingName:[className UTF8String] inXMLNode:_node->children inArray:array allowPartial:partial];
return array;
@@ -282,7 +312,7 @@ -(NSArray*)findChildrenWithAttribute:(NSString*)attribute matchingName:(NSString
-(NSArray*)findChildrenOfClass:(NSString*)className
-{
+{
return [self findChildrenWithAttribute:@"class" matchingName:className allowPartial:NO];
}
@@ -295,16 +325,46 @@ -(id)initWithXMLNode:(xmlNode*)xmlNode
return self;
}
++ (id)nodeWithName:(NSString *)name
+{
+ xmlNode *n = xmlNewNode(NULL, (xmlChar *)[name UTF8String]);
+
+ return JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:n]);
+}
+
+- (void)setAttributeNamed:(NSString *)name withValue:(NSString *)value
+{
+ const char *nameStr = [name UTF8String];
+ const char *valueStr = [value UTF8String];
+
+ setAttributeNamed(_node, nameStr, valueStr);
+}
+
+- (void)addAttributeNamed:(NSString *)name withValue:(NSString *)value
+{
+ const xmlChar *nameStr = (xmlChar *)[name UTF8String];
+ const xmlChar *valueStr = (xmlChar *)[value UTF8String];
+
+ xmlNewProp(_node, nameStr, valueStr);
+}
+
+-(void)removeAttributeNamed:(NSString *)name
+{
+ const xmlChar *nameStr = (xmlChar *) [name UTF8String];
+
+ xmlUnsetProp(_node, nameStr);
+}
+
-(void)appendChildContentsToString:(NSMutableString*)string inNode:(xmlNode*)node
{
if (node == NULL)
return;
- xmlNode *cur_node = NULL;
- for (cur_node = node; cur_node; cur_node = cur_node->next)
+ xmlNode *cur_node = NULL;
+ for (cur_node = node; cur_node; cur_node = cur_node->next)
{
if (cur_node->content)
- {
+ {
[string appendString:[NSString stringWithCString:(void*)cur_node->content encoding:NSUTF8StringEncoding]];
}
@@ -385,18 +445,20 @@ -(NSString*)allContents
}
NSString * rawContentsOfNode(xmlNode * node)
-{
+{
xmlBufferPtr buffer = xmlBufferCreateSize(1000);
xmlOutputBufferPtr buf = xmlOutputBufferCreateBuffer(buffer, NULL);
htmlNodeDumpOutput(buf, node->doc, node, (const char*)node->doc->encoding);
-
+
xmlOutputBufferFlush(buf);
-
+
NSString * string = nil;
if (buffer->content) {
- string = [[[NSString alloc] initWithBytes:(const void *)xmlBufferContent(buffer) length:xmlBufferLength(buffer) encoding:NSUTF8StringEncoding] autorelease];
+ string = JX_AUTORELEASE([[NSString alloc] initWithBytes:(const void *)xmlBufferContent(buffer)
+ length:xmlBufferLength(buffer)
+ encoding:NSUTF8StringEncoding]);
}
xmlOutputBufferClose(buf);
@@ -409,4 +471,128 @@ -(NSString*)rawContents {
return rawContentsOfNode(_node);
}
+-(NSString*)innerHTML {
+ NSMutableString *string = [NSMutableString string];
+ for (HTMLNode *child in [self children]) {
+ [string appendString:[child rawContents]];
+ }
+ return string;
+}
+
+-(NSArray*)nodesForXPath:(NSString*)query{
+ if (!query || ![query length]) {
+ NSLog(@"Unable to create XPath context. The query is empty.");
+ return nil;
+ }
+ xmlDocPtr doc = _node->doc;
+
+ xmlXPathContextPtr xpathCtx;
+ xmlXPathObjectPtr xpathObj;
+
+ /* Create xpath evaluation context */
+ xpathCtx = xmlXPathNewContext(doc);
+ if(xpathCtx == NULL)
+ {
+ NSLog(@"Unable to create XPath context.");
+ return nil;
+ }
+
+ /* Evaluate xpath expression */
+ xpathObj = xmlXPathEvalExpression((xmlChar *)[query cStringUsingEncoding:NSUTF8StringEncoding], xpathCtx);
+ if(xpathObj == NULL) {
+ NSLog(@"Unable to evaluate XPath.");
+ return nil;
+ }
+
+ xmlNodeSetPtr nodes = xpathObj->nodesetval;
+ if (!nodes)
+ {
+ NSLog(@"Nodes was nil.");
+ return nil;
+ }
+
+ NSMutableArray *resultNodes = [NSMutableArray array];
+ for (NSInteger i = 0; i < nodes->nodeNr; i++)
+ {
+ HTMLNode* node = JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:nodes->nodeTab[i]]);
+ [resultNodes addObject:node];
+ }
+
+ /* Cleanup */
+ xmlXPathFreeObject(xpathObj);
+ xmlXPathFreeContext(xpathCtx);
+
+ return resultNodes;
+}
+
+#pragma mark - Flip Studio mods
+
+- (NSArray *)childrenForXPath:(NSString *)xpath
+{
+ NSMutableArray *children = [[NSMutableArray alloc] init];
+
+ xmlXPathContextPtr context;
+ context = xmlXPathNewContext(_node->doc);
+ context->node = _node;
+
+ xmlXPathObjectPtr result;
+ result = xmlXPathEvalExpression((xmlChar *)[xpath UTF8String], context);
+ xmlXPathFreeContext (context);
+
+ xmlNodeSetPtr nodeSet;
+ nodeSet = result->nodesetval;
+ if (!xmlXPathNodeSetIsEmpty(nodeSet))
+ {
+ int i;
+ for (i = 0; i < nodeSet->nodeNr; i++)
+ {
+ xmlNodePtr nodePtr;
+ nodePtr = nodeSet->nodeTab[i];
+
+ HTMLNode *nNode = [[HTMLNode alloc] initWithXMLNode:nodePtr];
+ [children addObject:nNode];
+ JX_RELEASE([nNode release]);
+ }
+ }
+ xmlXPathFreeObject(result);
+
+ NSArray *array = [NSArray arrayWithArray:children];
+ JX_RELEASE([children release]);
+
+ return array;
+}
+
+- (void)setContent:(NSString *)content
+{
+ if (content != nil)
+ xmlNodeSetContent(_node, (xmlChar *)[content UTF8String]);
+}
+
+- (void)addNextSibling:(HTMLNode *)child
+{
+ xmlAddNextSibling(_node, child->_node);
+}
+
+- (void)addPrevSibling:(HTMLNode *)child
+{
+ xmlAddPrevSibling(_node, child->_node);
+}
+
+- (void)addChild:(HTMLNode *)child
+{
+ child->_node = xmlAddChild(_node, child->_node);
+}
+
+- (void)removeFromParent
+{
+ xmlUnlinkNode(_node);
+}
+
+- (id)copyWithZone:(NSZone *)zone
+{
+ xmlNodePtr nodeCopy = xmlCopyNode(_node, 1);
+
+ return JX_AUTORELEASE([[HTMLNode allocWithZone:zone] initWithXMLNode:nodeCopy]);
+}
+
@end
View
9 HTMLParser.h
@@ -18,9 +18,12 @@
htmlDocPtr _doc;
}
--(id)initWithContentsOfURL:(NSURL*)url error:(NSError**)error;
--(id)initWithData:(NSData*)data error:(NSError**)error;
--(id)initWithString:(NSString*)string error:(NSError**)error;
+-(id)initWithContentsOfURL:(NSURL*)url
+ error:(NSError**)error;
+-(id)initWithData:(NSData*)data
+ error:(NSError**)error;
+-(id)initWithString:(NSString*)string
+ error:(NSError**)error;
//Returns the doc tag
-(HTMLNode*)doc;
View
24 HTMLParser.m
@@ -8,6 +8,7 @@
#import "HTMLParser.h"
+#import "JXArcCompatibilityMacros.h"
@implementation HTMLParser
@@ -16,7 +17,7 @@ -(HTMLNode*)doc
if (_doc == NULL)
return NULL;
- return [[[HTMLNode alloc] initWithXMLNode:(xmlNode*)_doc] autorelease];
+ return JX_AUTORELEASE([[HTMLNode alloc] initWithXMLNode:(xmlNode*)_doc]);
}
-(HTMLNode*)html
@@ -24,7 +25,7 @@ -(HTMLNode*)html
if (_doc == NULL)
return NULL;
- return [[self doc] findChildTag:@"html"];
+ return [[self doc] findChildWithTag:@"html"];
}
-(HTMLNode*)head
@@ -32,7 +33,7 @@ -(HTMLNode*)head
if (_doc == NULL)
return NULL;
- return [[self doc] findChildTag:@"head"];
+ return [[self doc] findChildWithTag:@"head"];
}
-(HTMLNode*)body
@@ -40,10 +41,11 @@ -(HTMLNode*)body
if (_doc == NULL)
return NULL;
- return [[self doc] findChildTag:@"body"];
+ return [[self doc] findChildWithTag:@"body"];
}
--(id)initWithString:(NSString*)string error:(NSError**)error
+-(id)initWithString:(NSString*)string
+ error:(NSError**)error
{
if (self = [super init])
{
@@ -71,7 +73,8 @@ -(id)initWithString:(NSString*)string error:(NSError**)error
return self;
}
--(id)initWithData:(NSData*)data error:(NSError**)error
+-(id)initWithData:(NSData*)data
+ error:(NSError**)error
{
if (self = [super init])
{
@@ -102,25 +105,27 @@ -(id)initWithData:(NSData*)data error:(NSError**)error
return self;
}
--(id)initWithContentsOfURL:(NSURL*)url error:(NSError**)error
+-(id)initWithContentsOfURL:(NSURL*)url
+ error:(NSError**)error
{
NSData * _data = [[NSData alloc] initWithContentsOfURL:url options:0 error:error];
if (_data == nil || *error)
{
- [_data release];
+ JX_RELEASE(_data);
return nil;
}
self = [self initWithData:_data error:error];
- [_data release];
+ JX_RELEASE(_data);
return self;
}
+#if (JX_HAS_ARC == 0)
-(void)dealloc
{
if (_doc)
@@ -130,5 +135,6 @@ -(void)dealloc
[super dealloc];
}
+#endif
@end
View
57 JXArcCompatibilityMacros.h
@@ -0,0 +1,57 @@
+//
+// JXArcCompatibilityMacros.h
+//
+// Created by Jan on 29.09.12.
+// Copyright 2012 Jan Weiß
+//
+// Based on “DDMathParser.h” by Dave DeLong.
+//
+// Released under the BSD software licence.
+//
+
+#ifndef JXArcCompatibilityMacros_h
+#define JXArcCompatibilityMacros_h
+
+#ifdef __clang__
+#define JX_STRONG strong
+#else
+#define JX_STRONG retain
+#endif
+
+/*
+Porting help (pretty crude, could use improvement):
+\[(.+) retain\] JX_RETAIN(\1)
+\[(.+) release\] JX_RELEASE(\1)
+\[(.+) autorelease\] JX_AUTORELEASE(\1)
+
+\(id\)([\w\d.]+|\[.+\]) JX_BRIDGED_CAST(id, \1)
+
+The above have usual problems with nesting. Don’t use them with “Replace all”!
+*/
+
+#if __has_feature(objc_arc)
+
+#define JX_HAS_ARC 1
+#define JX_RETAIN(_o) (_o)
+#define JX_RELEASE(_o)
+#define JX_AUTORELEASE(_o) (_o)
+
+#define JX_BRIDGED_CAST(_type, _o) (__bridge _type)(_o)
+#define JX_TRANSFER_OBJC_TO_CF(_type, _o) (__bridge_retained _type)(_o)
+#define JX_TRANSFER_CF_TO_OBJC(_type, _o) (__bridge_transfer _type)(_o)
+
+#else
+
+#define JX_HAS_ARC 0
+#define JX_RETAIN(_o) [(_o) retain]
+#define JX_RELEASE(_o) [(_o) release]
+#define JX_AUTORELEASE(_o) [(_o) autorelease]
+
+#define JX_BRIDGED_CAST(_type, _o) (_type)(_o)
+#define JX_TRANSFER_OBJC_TO_CF(_type, _o) (_type)((_o) ? CFRetain((CFTypeRef)(_o)) : NULL)
+#define JX_TRANSFER_CF_TO_OBJC(_type, _o) [(_type)CFMakeCollectable(_o) autorelease]
+
+#endif
+
+
+#endif
View
7 LICENSE.md
@@ -0,0 +1,7 @@
+Copyright (C) 2010-2012 Ben Reeves and contributors
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
View
36 README.md
@@ -4,39 +4,5 @@
Example Usage
=============
-```objc
-NSError *error = nil;
-NSString *html =
- @"<ul>"
- "<li><input type='image' name='input1' value='string1value' /></li>"
- "<li><input type='image' name='input2' value='string2value' /></li>"
- "</ul>"
- "<span class='spantext'><b>Hello World 1</b></span>"
- "<span class='spantext'><b>Hello World 2</b></span>";
-HTMLParser *parser = [[HTMLParser alloc] initWithString:html error:&error];
-if (error) {
- NSLog(@"Error: %@", error);
- return;
-}
-
-HTMLNode *bodyNode = [parser body];
-
-NSArray *inputNodes = [bodyNode findChildTags:@"input"];
-
-for (HTMLNode *inputNode in inputNodes) {
- if ([[inputNode getAttributeNamed:@"name"] isEqualToString:@"input2"]) {
- NSLog(@"%@", [inputNode getAttributeNamed:@"value"]); //Answer to first question
- }
-}
-
-NSArray *spanNodes = [bodyNode findChildTags:@"span"];
-
-for (HTMLNode *spanNode in spanNodes) {
- if ([[spanNode getAttributeNamed:@"class"] isEqualToString:@"spantext"]) {
- NSLog(@"%@", [spanNode rawContents]); //Answer to second question
- }
-}
-
-[parser release];
-```
+See `example.m`.
View
57 example.m
@@ -0,0 +1,57 @@
+//
+// example.m
+// Objective-C-HMTL-Parser
+//
+// Created by Jan on 27.11.12.
+//
+//
+
+#import <Foundation/Foundation.h>
+
+#import "HTMLParser.h"
+
+#import "JXArcCompatibilityMacros.h"
+
+int main(int argc, const char * argv[])
+{
+
+ @autoreleasepool {
+
+ NSError *error = nil;
+ NSString *html =
+ @"<ul>"
+ "<li><input type='image' name='input1' value='string1value' /></li>"
+ "<li><input type='image' name='input2' value='string2value' /></li>"
+ "</ul>"
+ "<span class='spantext'><b>Hello World 1</b></span>"
+ "<span class='spantext'><b>Hello World 2</b></span>";
+
+ HTMLParser *parser = [[HTMLParser alloc] initWithString:html error:&error];
+
+ if (error) {
+ NSLog(@"Error: %@", error);
+ return EXIT_FAILURE;
+ }
+
+ HTMLNode *bodyNode = [parser body];
+
+ NSArray *inputNodes = [bodyNode findChildrenWithTag:@"input"];
+
+ for (HTMLNode *inputNode in inputNodes) {
+ if ([[inputNode getAttributeNamed:@"name"] isEqualToString:@"input2"]) {
+ NSLog(@"%@", [inputNode getAttributeNamed:@"value"]); //Answer to first question
+ }
+ }
+
+ NSArray *spanNodes = [bodyNode findChildrenWithTag:@"span"];
+
+ for (HTMLNode *spanNode in spanNodes) {
+ if ([[spanNode getAttributeNamed:@"class"] isEqualToString:@"spantext"]) {
+ NSLog(@"%@", [spanNode rawContents]); //Answer to second question
+ }
+ }
+
+ JX_RELEASE(parser);
+
+ }
+}
Something went wrong with that request. Please try again.