Added wxWrapperInputStream class.
This stream allows to wrap another stream. This is a useful base class for adapter classes providing stream interface on top of something else, like the upcoming wxFSInputStream. See #14185. git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@71205 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
@@ -640,6 +640,54 @@ protected:
|
||||
inline wxStreamBuffer *wxBufferedOutputStream::OutputStreamBuffer() const { return m_o_streambuf; }
|
||||
#endif // WXWIN_COMPATIBILITY_2_6
|
||||
|
||||
// ---------------------------------------------------------------------------
|
||||
// wxWrapperInputStream: forwards all IO to another stream.
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
class WXDLLIMPEXP_BASE wxWrapperInputStream : public wxFilterInputStream
|
||||
{
|
||||
public:
|
||||
// Constructor fully initializing the stream. The overload taking pointer
|
||||
// takes ownership of the parent stream, the one taking reference does not.
|
||||
//
|
||||
// Notice that this class also has a default ctor but it's protected as the
|
||||
// derived class is supposed to take care of calling InitParentStream() if
|
||||
// it's used.
|
||||
wxWrapperInputStream(wxInputStream& stream);
|
||||
wxWrapperInputStream(wxInputStream* stream);
|
||||
|
||||
// Override the base class methods to forward to the wrapped stream.
|
||||
virtual wxFileOffset GetLength() const;
|
||||
virtual bool IsSeekable() const;
|
||||
|
||||
protected:
|
||||
virtual size_t OnSysRead(void *buffer, size_t size);
|
||||
virtual wxFileOffset OnSysSeek(wxFileOffset pos, wxSeekMode mode);
|
||||
virtual wxFileOffset OnSysTell() const;
|
||||
|
||||
// Ensure that our own last error is the same as that of the real stream.
|
||||
//
|
||||
// This method is const because the error must be updated even from const
|
||||
// methods (in other words, it really should have been mutable in the first
|
||||
// place).
|
||||
void SynchronizeLastError() const
|
||||
{
|
||||
const_cast<wxWrapperInputStream*>(this)->
|
||||
Reset(m_parent_i_stream->GetLastError());
|
||||
}
|
||||
|
||||
// Default constructor, use InitParentStream() later.
|
||||
wxWrapperInputStream();
|
||||
|
||||
// Set up the wrapped stream for an object initialized using the default
|
||||
// constructor. The ownership logic is the same as above.
|
||||
void InitParentStream(wxInputStream& stream);
|
||||
void InitParentStream(wxInputStream* stream);
|
||||
|
||||
wxDECLARE_NO_COPY_CLASS(wxWrapperInputStream);
|
||||
};
|
||||
|
||||
|
||||
#endif // wxUSE_STREAMS
|
||||
|
||||
#endif // _WX_WXSTREAM_H__
|
||||
|
@@ -1066,3 +1066,57 @@ public:
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
@class wxWrapperInputStream
|
||||
|
||||
A wrapper input stream is a kind of filter stream which forwards all the
|
||||
operations to its base stream. This is useful to build utility classes such
|
||||
as wxFSInputStream.
|
||||
|
||||
@note
|
||||
The interface of this class is the same as that of wxInputStream.
|
||||
Only a constructor differs and it is documented below.
|
||||
|
||||
@library{wxbase}
|
||||
@category{streams}
|
||||
|
||||
@see wxFSInputStream, wxFilterInputStream
|
||||
@since 2.9.4
|
||||
*/
|
||||
class wxWrapperInputStream : public wxFilterInputStream
|
||||
{
|
||||
public:
|
||||
//@{
|
||||
/**
|
||||
Initializes a wrapper stream.
|
||||
|
||||
If the parent stream is passed as a pointer then the new wrapper stream
|
||||
takes ownership of it. If it is passed by reference then it does not.
|
||||
*/
|
||||
wxWrapperInputStream(wxInputStream& stream);
|
||||
wxWrapperInputStream(wxInputStream* stream);
|
||||
//@}
|
||||
|
||||
protected:
|
||||
/**
|
||||
Default constructor, use InitParentStream() to finish initialization.
|
||||
|
||||
This constructor can be used by the derived classes from their own
|
||||
constructors when the parent stream can't be specified immediately.
|
||||
The derived class must call InitParentStream() later to do it.
|
||||
*/
|
||||
wxWrapperInputStream();
|
||||
|
||||
//@{
|
||||
/**
|
||||
Set up the wrapped stream for an object initialized using the default
|
||||
constructor.
|
||||
|
||||
The ownership logic is the same as for the non-default constructor,
|
||||
i.e. this object takes ownership of the stream if it's passed by
|
||||
pointer but not if it's passed by reference.
|
||||
*/
|
||||
void InitParentStream(wxInputStream& stream);
|
||||
void InitParentStream(wxInputStream* stream);
|
||||
//@}
|
||||
};
|
||||
|
@@ -36,6 +36,7 @@
|
||||
#include <ctype.h>
|
||||
#include "wx/datstrm.h"
|
||||
#include "wx/textfile.h"
|
||||
#include "wx/scopeguard.h"
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
// constants
|
||||
@@ -1446,6 +1447,93 @@ void wxBufferedOutputStream::SetOutputStreamBuffer(wxStreamBuffer *buffer)
|
||||
m_o_streambuf = buffer;
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------
|
||||
// wxWrapperInputStream implementation
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
wxWrapperInputStream::wxWrapperInputStream()
|
||||
{
|
||||
m_lasterror = wxSTREAM_READ_ERROR;
|
||||
}
|
||||
|
||||
wxWrapperInputStream::wxWrapperInputStream(wxInputStream& stream)
|
||||
: wxFilterInputStream(stream)
|
||||
{
|
||||
SynchronizeLastError();
|
||||
}
|
||||
|
||||
wxWrapperInputStream::wxWrapperInputStream(wxInputStream *stream)
|
||||
: wxFilterInputStream(stream)
|
||||
{
|
||||
if ( m_parent_i_stream )
|
||||
SynchronizeLastError();
|
||||
else
|
||||
m_lasterror = wxSTREAM_READ_ERROR;
|
||||
}
|
||||
|
||||
void wxWrapperInputStream::InitParentStream(wxInputStream& stream)
|
||||
{
|
||||
wxCHECK_RET( !m_parent_i_stream, "Can't init parent stream twice" );
|
||||
|
||||
m_parent_i_stream = &stream;
|
||||
|
||||
SynchronizeLastError();
|
||||
}
|
||||
|
||||
void wxWrapperInputStream::InitParentStream(wxInputStream* stream)
|
||||
{
|
||||
wxCHECK_RET( !m_parent_i_stream, "Can't init parent stream twice" );
|
||||
|
||||
m_parent_i_stream = stream;
|
||||
|
||||
if ( m_parent_i_stream )
|
||||
{
|
||||
m_owns = true;
|
||||
|
||||
SynchronizeLastError();
|
||||
}
|
||||
}
|
||||
|
||||
wxFileOffset wxWrapperInputStream::GetLength() const
|
||||
{
|
||||
wxCHECK_MSG(m_parent_i_stream, wxInvalidOffset, "Stream not valid");
|
||||
|
||||
wxON_BLOCK_EXIT_THIS0(wxWrapperInputStream::SynchronizeLastError);
|
||||
return m_parent_i_stream->GetLength();
|
||||
}
|
||||
|
||||
bool wxWrapperInputStream::IsSeekable() const
|
||||
{
|
||||
wxCHECK_MSG(m_parent_i_stream, false, "Stream not valid");
|
||||
return m_parent_i_stream->IsSeekable();
|
||||
}
|
||||
|
||||
size_t wxWrapperInputStream::OnSysRead(void *buffer, size_t size)
|
||||
{
|
||||
wxCHECK_MSG(m_parent_i_stream, false, "Stream not valid");
|
||||
|
||||
wxON_BLOCK_EXIT_THIS0(wxWrapperInputStream::SynchronizeLastError);
|
||||
|
||||
m_parent_i_stream->Read(buffer, size);
|
||||
return m_parent_i_stream->LastRead();
|
||||
}
|
||||
|
||||
wxFileOffset wxWrapperInputStream::OnSysSeek(wxFileOffset pos, wxSeekMode mode)
|
||||
{
|
||||
wxCHECK_MSG(IsSeekable(), false, "Stream not seekable");
|
||||
|
||||
wxON_BLOCK_EXIT_THIS0(wxWrapperInputStream::SynchronizeLastError);
|
||||
return m_parent_i_stream->SeekI (pos, mode);
|
||||
}
|
||||
|
||||
wxFileOffset wxWrapperInputStream::OnSysTell() const
|
||||
{
|
||||
wxCHECK_MSG(m_parent_i_stream, false, "Stream not valid");
|
||||
|
||||
wxON_BLOCK_EXIT_THIS0(wxWrapperInputStream::SynchronizeLastError);
|
||||
return m_parent_i_stream->TellI();
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
// Some IOManip function
|
||||
// ----------------------------------------------------------------------------
|
||||
|
Reference in New Issue
Block a user