arabica/include/XSLT/impl/handler/xslt_template_handler.hpp

133 lines
4.4 KiB
C++
Raw Normal View History

2007-07-19 19:01:42 +02:00
#ifndef ARABICA_XSLT_TEMPLATE_HANDLER_HPP
#define ARABICA_XSLT_TEMPLATE_HANDLER_HPP
#include "../xslt_template.hpp"
#include "xslt_item_container_handler.hpp"
namespace Arabica
{
namespace XSLT
{
2012-11-06 08:50:57 +01:00
template<class string_type, class string_adaptor>
class TemplateHandler : public ItemContainerHandler<Template<string_type, string_adaptor> >
2007-07-19 19:01:42 +02:00
{
2012-11-06 08:50:57 +01:00
typedef ItemContainerHandler<Template<string_type, string_adaptor> > baseT;
2007-07-19 19:01:42 +02:00
public:
2012-11-06 08:50:57 +01:00
TemplateHandler(CompilationContext<string_type, string_adaptor>& context) :
baseT(context),
2007-07-19 19:01:42 +02:00
done_params_(false)
{
} // TemplateHandler
2007-11-23 00:02:08 +01:00
virtual void characters(const std::string& ch)
{
if(!done_params_)
{
2012-11-06 08:53:00 +01:00
for(typename string_type::const_iterator i = ch.begin(), e = ch.end(); i != e; ++i)
2007-11-23 00:02:08 +01:00
if(!Arabica::XML::is_space(*i))
{
done_params_ = true;
break;
} // if ...
} // if(!done_params_)
2012-11-06 08:50:57 +01:00
baseT::characters(ch);
2007-11-23 00:02:08 +01:00
} // characters
2007-07-19 19:01:42 +02:00
protected:
2012-11-06 08:50:57 +01:00
virtual Template<string_type, string_adaptor>* createContainer(const string_type& /* namespaceURI */,
const string_type& /* localName */,
const string_type& qName,
const SAX::Attributes<string_type, string_adaptor>& atts)
2007-07-19 19:01:42 +02:00
{
2010-01-11 10:02:17 +01:00
static const ValueRule rules[] = { { "match", false, 0, 0 },
{ "mode", false, 0, 0 },
{ "name", false, 0, 0 },
{ "priority", false, 0, 0 },
{ 0, false, 0, 0 } };
2012-11-06 08:50:57 +01:00
std::map<string_type, string_type> attributes = gatherAttributes(qName, atts, rules);
2012-11-06 08:50:57 +01:00
const string_type& match = attributes["match"];
if((match == "") && (attributes["name"] == ""))
2007-07-19 19:01:42 +02:00
throw SAX::SAXException("xsl:template must have a match and/or a name attribute");
int index = atts.getIndex("mode");
if(index != -1)
{
2012-11-06 08:50:57 +01:00
const string_type& mode = attributes["mode"];
if(mode == "")
throw SAX::SAXException("xsl:template mode cannot be empty");
if(match == "")
throw SAX::SAXException("xsl:template may not have a mode without a match");
} // ...
2007-07-19 19:01:42 +02:00
2012-11-06 08:50:57 +01:00
const string_type& priority = attributes["priority"];
if((atts.getIndex("priority") != -1) && (priority == ""))
throw SAX::SAXException("xsl:template priority cannot be empty");
2012-11-06 08:50:57 +01:00
string_type name;
if(attributes["name"] != "")
2012-11-06 08:50:57 +01:00
name = baseT::context().processInternalQName(attributes["name"]).clarkName();
2007-10-26 14:28:48 +02:00
2012-11-06 08:50:57 +01:00
string_type mode;
if(attributes["mode"] != "")
2012-11-06 08:50:57 +01:00
mode = baseT::context().processInternalQName(attributes["mode"]).clarkName();
2007-10-26 21:12:27 +02:00
2007-07-19 19:01:42 +02:00
if(match == "")
2012-11-06 08:50:57 +01:00
return new Template<string_type, string_adaptor>(name,
mode,
priority,
2012-11-06 08:50:57 +01:00
baseT::context().precedence());
2007-07-19 19:01:42 +02:00
2012-11-06 08:50:57 +01:00
return new Template<string_type, string_adaptor>(baseT::context().xpath_match(match),
name,
mode,
priority,
2012-11-06 08:50:57 +01:00
baseT::context().precedence());
2007-07-19 19:01:42 +02:00
} // createContainer
2012-11-06 08:50:57 +01:00
virtual bool createChild(const string_type& namespaceURI,
const string_type& localName,
const string_type& qName,
const SAX::Attributes<string_type, string_adaptor>& atts)
2007-07-19 19:01:42 +02:00
{
if((namespaceURI == StylesheetConstant::NamespaceURI()) &&
(localName == "param"))
{
if(!done_params_)
{
2012-11-06 08:53:00 +01:00
baseT::context().push(baseT::container(),
2012-11-06 08:50:57 +01:00
new VariableHandler<Param>(baseT::context()),
2007-07-19 19:01:42 +02:00
namespaceURI,
localName,
qName,
2007-07-19 19:01:42 +02:00
atts);
return true;
}
else
throw SAX::SAXException("xsl:param must immediately follow xsl:template");
}
done_params_ = true;
2012-11-06 08:50:57 +01:00
return baseT::createChild(namespaceURI, localName, qName, atts);
2007-07-19 19:01:42 +02:00
} // createChild
public:
2012-11-06 08:50:57 +01:00
virtual void endElement(const string_type& /* namespaceURI */,
const string_type& /* localName */,
const string_type& /* qName */)
2007-07-19 19:01:42 +02:00
{
2012-11-06 08:53:00 +01:00
baseT::context().stylesheet().add_template(baseT::container());
2012-11-06 08:50:57 +01:00
baseT::context().pop();
2007-07-19 19:01:42 +02:00
} // endElement
private:
bool done_params_;
}; // class TemplateHandler
} // namespace XSLT
} // namespace Arabica
#endif // ARABICA_XSLT_TEMPLATE_HANDLER_HPP