1 /////////////////////////////////////////////////////////////////////////////
2 // Name: wx/stdstream.h
3 // Purpose: Implementation of std::istream and std::ostream derived
4 // wrappers for wxInputStream and wxOutputStream
5 // Author: Jonathan Liu <net147@gmail.com>
8 // Copyright: (c) 2009 Jonathan Liu
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
12 // ==========================================================================
14 // ==========================================================================
16 // For compilers that support precompilation, includes "wx.h".
17 #include "wx/wxprec.h"
23 #if wxUSE_STD_IOSTREAM
28 #include "wx/stdstream.h"
35 // ==========================================================================
37 // ==========================================================================
43 IosSeekDirToWxSeekMode(std::ios_base::seekdir way,
48 case std::ios_base::beg:
49 seekMode = wxFromStart;
51 case std::ios_base::cur:
52 seekMode = wxFromCurrent;
54 case std::ios_base::end:
64 } // anonymous namespace
66 // ==========================================================================
67 // wxStdInputStreamBuffer
68 // ==========================================================================
70 wxStdInputStreamBuffer::wxStdInputStreamBuffer(wxInputStream& stream) :
71 m_stream(stream), m_lastChar(EOF)
76 wxStdInputStreamBuffer::setbuf(char *WXUNUSED(s),
77 std::streamsize WXUNUSED(n))
83 wxStdInputStreamBuffer::seekoff(std::streamoff off,
84 std::ios_base::seekdir way,
85 std::ios_base::openmode which)
89 if ( !IosSeekDirToWxSeekMode(way, seekMode) )
91 if ( !(which & std::ios_base::in) )
94 off_t newPos = m_stream.SeekI((off_t) off, seekMode);
96 if ( newPos != wxInvalidOffset )
97 return (std::streampos) newPos;
103 wxStdInputStreamBuffer::seekpos(std::streampos sp,
104 std::ios_base::openmode which)
106 if ( !(which & std::ios_base::in) )
109 off_t newPos = m_stream.SeekI((off_t) sp);
111 if ( newPos != wxInvalidOffset )
112 return (std::streampos) newPos;
118 wxStdInputStreamBuffer::showmanyc()
120 if ( m_stream.CanRead() && (off_t) m_stream.GetSize() > m_stream.TellI() )
121 return m_stream.GetSize() - m_stream.TellI();
127 wxStdInputStreamBuffer::xsgetn(char *s, std::streamsize n)
129 m_stream.Read((void *) s, (size_t) n);
131 std::streamsize read = m_stream.LastRead();
134 m_lastChar = (unsigned char) s[read - 1];
140 wxStdInputStreamBuffer::underflow()
142 int ch = m_stream.GetC();
144 if ( m_stream.LastRead() == 1 )
146 m_stream.Ungetch((char) ch);
156 wxStdInputStreamBuffer::uflow()
158 int ch = m_stream.GetC();
160 if ( m_stream.LastRead() == 1 )
172 wxStdInputStreamBuffer::pbackfail(int c)
176 if ( m_lastChar == EOF )
183 return m_stream.Ungetch((char) c) ? c : EOF;
186 // ==========================================================================
187 // wxStdOutputStreamBuffer
188 // ==========================================================================
190 wxStdOutputStreamBuffer::wxStdOutputStreamBuffer(wxOutputStream& stream) :
196 wxStdOutputStreamBuffer::setbuf(char *WXUNUSED(s),
197 std::streamsize WXUNUSED(n))
203 wxStdOutputStreamBuffer::seekoff(std::streamoff off,
204 std::ios_base::seekdir way,
205 std::ios_base::openmode which)
209 if ( !IosSeekDirToWxSeekMode(way, seekMode) )
211 if ( !(which & std::ios_base::out) )
214 off_t newPos = m_stream.SeekO((off_t) off, seekMode);
216 if ( newPos != wxInvalidOffset )
217 return (std::streampos) newPos;
223 wxStdOutputStreamBuffer::seekpos(std::streampos sp,
224 std::ios_base::openmode which)
226 if ( !(which & std::ios_base::out) )
229 off_t newPos = m_stream.SeekO((off_t) sp);
231 if ( newPos != wxInvalidOffset )
232 return (std::streampos) newPos;
238 wxStdOutputStreamBuffer::xsputn(const char *s,
241 m_stream.Write((const void *) s, (size_t) n);
242 return (std::streamsize) m_stream.LastWrite();
246 wxStdOutputStreamBuffer::overflow(int c)
249 return m_stream.IsOk() ? c : EOF;
252 // ==========================================================================
253 // wxStdInputStream and wxStdOutputStream
254 // ==========================================================================
256 // FIXME-VC6: it is impossible to call basic_ios<char>::init() with this
257 // compiler, it complains about invalid call to non-static member
258 // function so use a suspicious (as it uses a pointer to not yet
259 // constructed streambuf) but working workaround
261 // It also doesn't like using istream in the ctor initializer list
262 // and we must spell it out as basic_istream<char>.
265 wxStdInputStream::wxStdInputStream(wxInputStream& stream)
266 : std::basic_istream<char, std::char_traits<char> >(&m_streamBuffer),
267 m_streamBuffer(stream)
271 wxStdOutputStream::wxStdOutputStream(wxOutputStream& stream)
272 : std::basic_ostream<char, std::char_traits<char> >(&m_streamBuffer),
273 m_streamBuffer(stream)
279 wxStdInputStream::wxStdInputStream(wxInputStream& stream) :
280 std::istream(NULL), m_streamBuffer(stream)
282 std::ios::init(&m_streamBuffer);
285 wxStdOutputStream::wxStdOutputStream(wxOutputStream& stream) :
286 std::ostream(NULL), m_streamBuffer(stream)
288 std::ios::init(&m_streamBuffer);
293 #endif // wxUSE_STD_IOSTREAM