Xalan-C++ API Documentation

The Xalan C++ XSLT Processor Version 1.10

Main Page   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members  

XalanOtherEncodingWriter.hpp

Go to the documentation of this file.
00001 /*
00002  * Copyright 1999-2004 The Apache Software Foundation.
00003  *
00004  * Licensed under the Apache License, Version 2.0 (the "License");
00005  * you may not use this file except in compliance with the License.
00006  * You may obtain a copy of the License at
00007  *
00008  *     http://www.apache.org/licenses/LICENSE-2.0
00009  *
00010  * Unless required by applicable law or agreed to in writing, software
00011  * distributed under the License is distributed on an "AS IS" BASIS,
00012  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00013  * See the License for the specific language governing permissions and
00014  * limitations under the License.
00015  */
00016 #if !defined(XALANUNICODESUBSETWRITER_HEADER_GUARD_1357924680)
00017 #define XALANUNICODESUBSETWRITER_HEADER_GUARD_1357924680
00018 
00019 
00020 #include <xalanc/XMLSupport/XalanFormatterWriter.hpp>
00021 
00022 
00023 
00024 XALAN_CPP_NAMESPACE_BEGIN
00025 
00026 
00027 
00028 
00029 template <class Predicate,
00030           class ConstantsType>
00031 class XalanOtherEncodingWriter : public XalanFormatterWriter
00032 {
00033 public:
00034 
00035     typedef XalanOtherEncodingWriter<Predicate, ConstantsType>  ThisType;
00036 
00037     class WriteCharRef
00038     {
00039     public:
00040 
00041         WriteCharRef(ThisType&  writer) :
00042             m_writer(writer)
00043         {
00044         }
00045 
00046         void
00047         operator()(unsigned int value) const
00048         {
00049             m_writer.writeNumericCharacterReference(value);
00050         }
00051 
00052     private:
00053 
00054         ThisType&   m_writer;
00055     };
00056 
00057     class ThrowTranscodingException
00058     {
00059     public:
00060 
00061         ThrowTranscodingException(ThisType&     writer) :
00062             m_writer(writer)
00063         {
00064         }
00065 
00066         void
00067         operator()(unsigned int  value) const
00068         {
00069             m_writer.throwInvalidCharacterException(value, m_writer.getMemoryManager());
00070         }
00071 
00072     private:
00073 
00074         ThisType&   m_writer;
00075     };
00076 
00077     friend class WriteCharRef;
00078     friend class ThrowTranscodingException;
00079 
00080     typedef XalanDOMChar    value_type;
00081 
00082     XalanOtherEncodingWriter(
00083                 Writer&         writer,
00084                 MemoryManager&  theMemoryManager) :
00085         XalanFormatterWriter(
00086             writer,
00087             theMemoryManager),
00088         m_buffer(),
00089         m_bufferPosition(m_buffer),
00090         m_bufferRemaining(kBufferSize),
00091         m_predicate(writer.getStream()),
00092         m_constants(),
00093         m_charRefFunctor(*this),
00094         m_exceptionFunctor(*this)
00095     {
00096     }
00097 
00098     virtual
00099     ~XalanOtherEncodingWriter()
00100     {
00101     }
00102 
00106     void
00107     outputNewline()
00108     {
00109         assert(m_newlineString != 0);
00110         assert(length(m_newlineString) == m_newlineStringLength);
00111 
00112         write(
00113             m_newlineString,
00114             m_newlineStringLength);
00115     }
00116 
00121     size_type
00122     writeCDATAChar(
00123                 const XalanDOMChar  chars[],
00124                 size_type           start,
00125                 size_type           length,
00126                 bool&               outsideCDATA)
00127     {
00128         assert(chars != 0 && length > 0 && start < length);
00129 
00130         const XalanDOMChar  theChar = chars[start];
00131 
00132         unsigned int value = theChar;
00133 
00134         size_type result = start;
00135 
00136         if (isUTF16HighSurrogate(theChar) == true)
00137         {
00138             if (start + 1 >= length)
00139             {
00140                 throwInvalidUTF16SurrogateException(
00141                     theChar, 
00142                     0,
00143                     getMemoryManager());
00144             }
00145             else 
00146             {
00147                 value = decodeUTF16SurrogatePair(theChar, chars[start+1],  getMemoryManager());
00148 
00149                 ++result;
00150             }
00151         }
00152 
00153         if(m_predicate(value))
00154         {
00155             if (outsideCDATA == false)
00156             {
00157                 // We have a representable char in the normal state,
00158                 // so just print it.
00159                 write(value);
00160             }
00161             else
00162             {
00163                 // The previous character was a not representable.
00164                 // Open the CDATA section again, print the character,
00165                 // then change the flag.
00166                 write(
00167                     m_constants.s_cdataOpenString,
00168                     m_constants.s_cdataOpenStringLength);
00169 
00170                 write(value);
00171 
00172                 outsideCDATA = false;
00173             }
00174         }
00175         else
00176         {
00177             if(outsideCDATA == false)
00178             {
00179                 // we have a non-representable char in the normal state - 
00180                 // close the CDATA section and print the value
00181                 write(
00182                     m_constants.s_cdataCloseString,
00183                     m_constants.s_cdataCloseStringLength);
00184 
00185                 writeNumericCharacterReference(value);
00186 
00187                 outsideCDATA = true;   
00188             }
00189             else
00190             {
00191                 writeNumericCharacterReference(value);
00192             }
00193         }        
00194 
00195         return result;
00196     }
00197 
00202     void
00203     writeNameChar(
00204             const XalanDOMChar*     data,
00205             size_type               theLength)
00206     {
00207         for( size_type i = 0; i < theLength; ++i)
00208         { 
00209             i = write(data, i , theLength, m_exceptionFunctor); 
00210         }
00211     }
00212 
00217     void
00218     writePIChars(
00219             const XalanDOMChar*     data,
00220             size_type               theLength)
00221     {
00222         for( size_type i = 0; i < theLength; )
00223         { 
00224             i = write(data, i , theLength, m_exceptionFunctor); 
00225         }
00226     }
00227 
00233     void
00234     writeCommentChars(
00235             const XalanDOMChar*     data,
00236             size_type               theLength)
00237     {
00238         for( size_type i = 0; i < theLength; )
00239         { 
00240             i = write(data, i , theLength, m_exceptionFunctor); 
00241         }
00242     }
00243 
00244     void
00245     write(
00246             const XalanDOMChar*     theChars,
00247             size_type               theLength)
00248     {
00249         for(size_type i = 0; i < theLength; ++i)
00250         {
00251             write(theChars[i]);
00252         }
00253     }
00254 
00255     void
00256     write(const XalanDOMString&     theChars)
00257     {
00258         write(theChars.c_str(), theChars.length());
00259     }
00260 
00265     void
00266     write(XalanDOMChar    theChar)
00267     {
00268         assert(
00269             isUTF16HighSurrogate(theChar) == false &&
00270             isUTF16LowSurrogate(theChar) == false);
00271 
00272         if (m_bufferRemaining == 0)
00273         {
00274             flushBuffer();
00275         }
00276 
00277         if(m_predicate(theChar))
00278         {
00279             *m_bufferPosition = theChar;
00280 
00281             ++m_bufferPosition;
00282             --m_bufferRemaining;
00283         }
00284         else
00285         {
00286             writeNumericCharacterReference(theChar);
00287         }
00288     }
00289 
00290     size_type
00291     write(
00292             const XalanDOMChar  chars[],
00293             size_type           start,
00294             size_type           length)
00295     {
00296 
00297         return write(chars, start, length, m_charRefFunctor);
00298     }
00299 
00300     void
00301     writeSafe(
00302             const XalanDOMChar*     theChars,
00303             size_type               theLength)
00304     {
00305         for(size_type i = 0; i < theLength; ++i)
00306         {
00307             const XalanDOMChar  ch = theChars[i];
00308 
00309             if (isUTF16HighSurrogate(ch) == true)
00310             {
00311                 if (i + 1 >= theLength)
00312                 {
00313                     throwInvalidUTF16SurrogateException(ch, 0,  getMemoryManager());
00314                 }
00315                 else 
00316                 {
00317                     unsigned int value = decodeUTF16SurrogatePair(ch, theChars[i+1],  getMemoryManager());
00318 
00319                     if(this->m_isPresentable(value))
00320                     {
00321                         write(value);
00322                     }
00323                     else
00324                     {
00325                         this->writeNumberedEntityReference(value);
00326                     }
00327 
00328                     ++i;
00329                 }
00330             }
00331             else
00332             {
00333                 write((unsigned int)ch);
00334             }
00335         }
00336     }
00337 
00338     void
00339     write(const XalanDOMChar*     theChars)
00340     {
00341         write(theChars, XalanDOMString::length(theChars));
00342     }
00343 
00344     void
00345     flushWriter()
00346     {
00347         m_writer.flush();
00348     }    
00349 
00350     void
00351     flushBuffer()
00352     {
00353         m_writer.write(m_buffer, 0, m_bufferPosition - m_buffer);
00354 
00355         m_bufferPosition = m_buffer;
00356         m_bufferRemaining = kBufferSize;
00357     }
00358 
00359 private:
00360 
00374 
00375     template <class TranscodingFailureFunctor>
00376     size_type
00377     write(
00378             const XalanDOMChar          chars[],
00379             size_type                   start,
00380             size_type                   length,
00381             TranscodingFailureFunctor&  failureHandler)
00382     {
00383         assert(chars != 0 && length > 0);
00384         assert(start <= length);
00385 
00386         size_type result = start;
00387 
00388         const XalanDOMChar  ch = chars[start];
00389 
00390         unsigned int value = ch;
00391 
00392         if (XalanFormatterWriter::isUTF16HighSurrogate(ch) == true)
00393         {
00394             if (start + 1 >= length)
00395             {
00396                 throwInvalidUTF16SurrogateException(
00397                     ch, 
00398                     0,
00399                     getMemoryManager());
00400             }
00401             else 
00402             {
00403                 value = decodeUTF16SurrogatePair(ch, chars[start+1],  getMemoryManager());
00404 
00405                 ++result;
00406             }
00407         }
00408 
00409         if(m_predicate(value))
00410         {
00411             write(value);
00412         }
00413         else
00414         {
00415             failureHandler(value);
00416         }
00417 
00418         return result;
00419     }
00420 
00427     void
00428     write(unsigned int  theChar)
00429     {
00430         // encode back UTF-32 into UTF-16 
00431 
00432         if( theChar > 0xFFFF )
00433         {
00434             if (m_bufferRemaining < 2)
00435             {
00436                 flushBuffer();
00437             }
00438 
00439             *m_bufferPosition = (XalanDOMChar((theChar >> 10) + 0xD7C0));
00440 
00441             ++m_bufferPosition;
00442 
00443             *m_bufferPosition = (XalanDOMChar((theChar &  0x03FF) + 0xDC00));
00444 
00445             ++m_bufferPosition;
00446 
00447             m_bufferRemaining = m_bufferRemaining - size_type(2);
00448         }   
00449         else
00450         {
00451             if (m_bufferRemaining == 0)
00452             {
00453                 flushBuffer();
00454             }
00455 
00456             *m_bufferPosition = XalanDOMChar(theChar);
00457 
00458             ++m_bufferPosition;
00459             --m_bufferRemaining;
00460         }  
00461     }
00462 
00463     void
00464     writeNumericCharacterReference(unsigned int     theNumber)
00465     {
00466         write(formatNumericCharacterReference(theNumber));
00467     }
00468 
00469     enum
00470     {
00471         kBufferSize = 512u  // The size of the buffer
00472     };
00473 
00474 
00475     // Data members...
00476     XalanDOMChar            m_buffer[kBufferSize];
00477 
00478     XalanDOMChar*           m_bufferPosition;
00479 
00480     size_type               m_bufferRemaining;
00481 
00482     const Predicate         m_predicate;
00483 
00484     const ConstantsType     m_constants;
00485 
00486     const WriteCharRef                  m_charRefFunctor;
00487 
00488     const ThrowTranscodingException     m_exceptionFunctor;
00489 };
00490 
00491 
00492 
00493 XALAN_CPP_NAMESPACE_END
00494 
00495 
00496 
00497 #endif  // XALANUNICODESUBSETWRITER_HEADER_GUARD_1357924680

Interpreting class diagrams

Doxygen and GraphViz are used to generate this API documentation from the Xalan-C header files.

dot

Xalan-C++ XSLT Processor Version 1.10
Copyright © 1999-2004 The Apache Software Foundation. All Rights Reserved.

Apache Logo