]>
git.saurik.com Git - wxWidgets.git/blob - utils/HelpGen/src/ifcontext.cpp
1 /////////////////////////////////////////////////////////////////////////////
3 // Purpose: Contrib. demo
4 // Author: Aleksandras Gluchovas
8 // Copyright: (c) Aleskandars Gluchovas
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
12 // For compilers that support precompilation, includes "wx/wx.h".
13 #include "wx/wxprec.h"
25 #include "ifcontext.h"
27 /***** Implementation for class spInterFileContext *****/
29 size_t spInterFileContext::GetFileNo( const wxString
& fname
)
31 for ( size_t i
= 0; i
!= m_Files
.size(); ++i
)
33 if ( fname
== m_Files
[i
] )
37 wxFAIL_MSG("File not found in array in function spInterFileContext::GetFileNo()");
42 size_t spInterFileContext::GetFileNoOfContext( spContext
& ctx
)
44 spContext
* pCtx
= ctx
.GetEnclosingContext( SP_CTX_FILE
);
46 // DBG:: outer-file context should be present
47 wxASSERT( pCtx
&& pCtx
->GetType() == SP_CTX_FILE
);
49 return GetFileNo( ((spFile
*)pCtx
)->m_FileName
);
52 /*** public interface ***/
54 spInterFileContext::spInterFileContext()
57 spInterFileContext::~spInterFileContext()
60 void spInterFileContext::AddFile( const wxString
& fname
, const wxString
& content
)
62 m_Files
.push_back( fname
);
63 m_Contents
.push_back( content
);
66 void spInterFileContext::RemoveContext( spContext
& ctx
)
68 wxASSERT( ctx
.PositionIsKnown() ); // DBG:: should be checked by-user code
70 size_t fNo
= GetFileNoOfContext( ctx
);
72 mDeletionMarks
.push_back( spBookmark( ctx
.mSrcOffset
, ctx
.mContextLength
, fNo
) );
75 void spInterFileContext::InsertBookmarkSorted( BookmarkListT
& lst
, spBookmark
& mark
)
77 for( size_t i
= 0; i
!= lst
.size(); ++i
)
79 if ( lst
[i
].mFrom
> mark
.mFrom
)
81 lst
.insert( &lst
[i
], mark
);
85 lst
.push_back( mark
);
88 void spInterFileContext::DoAppendSourceFragment( wxString
& source
,
90 size_t pos
, size_t len
)
92 mFiltered
.erase( mFiltered
.begin(), mFiltered
.end() );
96 for( i
= 0; i
!= mDeletionMarks
.size(); ++i
)
98 spBookmark
& mark
= mDeletionMarks
[i
];
100 if ( mark
.mFileNo
== mCurFileNo
&&
101 mark
.mFrom
>= pos
&& mark
.mFrom
< pos
+ len
)
103 InsertBookmarkSorted( mFiltered
, mark
);
108 for( i
= 0; i
!= mFiltered
.size(); ++ i
)
110 spBookmark
& mark
= mFiltered
[i
];
112 result
.append( source
, cur
, ( (size_t)mark
.mFrom
- cur
) );
114 cur
= size_t( mark
.mFrom
+ mark
.mLen
);
116 if ( cur
>= pos
+ len
) // check if we've overstepped the current source-fragment
118 // wxASSERT(0); // DBG:: with current imp. this should not happen
119 wxFAIL_MSG("Overstepped the current source fragment in function\nspInterFileContext::DoAppendSourceFragment()");
120 cur
= pos
+ len
; break;
124 result
.append( source
, cur
, ( pos
+ len
) - cur
);
127 void spInterFileContext::GenerateContextBody( spContext
& ctx
,
130 size_t& lastSavedPos
,
131 size_t& lastKnownPos
)
133 if ( ctx
.PositionIsKnown() )
134 lastKnownPos
= ctx
.mSrcOffset
;
136 if ( ctx
.IsVirtualContext() )
138 // add fragment accumulated before this context
140 DoAppendSourceFragment( source
, result
,
141 size_t(lastSavedPos
),
142 size_t(lastKnownPos
- lastSavedPos
) );
146 result
+= ctx
.GetVirtualContextBody();
148 lastSavedPos
= lastKnownPos
;
150 if ( ctx
.PositionIsKnown() )
152 if ( ctx
.VitualContextHasChildren() )
154 lastKnownPos
= ctx
.mSrcOffset
+ ctx
.mHeaderLength
;
156 lastSavedPos
= lastKnownPos
;
160 lastKnownPos
= ctx
.mSrcOffset
+ ctx
.mContextLength
;
162 lastSavedPos
= lastKnownPos
;
164 return; // have not children
169 MMemberListT
& lst
= ctx
.GetMembers();
171 for( size_t i
= 0; i
!= lst
.size(); ++i
)
173 GenerateContextBody( *lst
[i
], source
, result
, lastSavedPos
, lastKnownPos
);
176 if ( ctx
.IsVirtualContext() )
178 if ( ctx
.VitualContextHasChildren() && !ctx
.GetFooterOfVirtualContextBody().empty() )
180 // append the reminder space after children of the context
182 DoAppendSourceFragment( result
, source
,
183 size_t(lastSavedPos
),
184 size_t(lastKnownPos
- lastSavedPos
) );
187 result
+= ctx
.GetFooterOfVirtualContextBody();
189 lastKnownPos
= ctx
.mSrcOffset
+ ctx
.mContextLength
;
191 lastSavedPos
= lastKnownPos
;
195 if ( ctx
.PositionIsKnown() )
197 lastKnownPos
= ctx
.mSrcOffset
+ ctx
.mContextLength
;
200 void spInterFileContext::GenrateContents()
202 MMemberListT
& lst
= GetMembers();
204 for( size_t f
= 0; f
!= lst
.size(); ++f
)
206 wxString
& fname
= ((spFile
*)lst
[f
])->m_FileName
;
208 size_t fileNo
= GetFileNo( fname
);
210 wxString
& source
= m_Contents
[ fileNo
];
214 size_t lastKnownPos
= 0, // the begining of the file is always "known"
219 GenerateContextBody( *lst
[f
], source
, result
, lastSavedPos
, lastKnownPos
);
221 // the end of file is always known
223 lastKnownPos
= m_Contents
[ fileNo
].length();
225 // append the reminder
227 DoAppendSourceFragment( source
, result
,
228 size_t(lastSavedPos
),
229 size_t(lastKnownPos
- lastSavedPos
) );
231 // replace original contnet with newly generated one
233 m_Contents
[ fileNo
] = result
;
237 void spInterFileContext::ParseContents( SourceParserPlugin
* pPlugin
)
239 mDeletionMarks
.erase( mDeletionMarks
.begin(), mDeletionMarks
.end() );
241 RemoveChildren(); // clean up top-level context
243 mParser
.SetPlugin( pPlugin
);
245 for( size_t i
= 0; i
!= m_Files
.size(); ++i
)
247 wxChar
* s
= (char*)(m_Contents
[i
].c_str());
249 spFile
* pFCtx
= mParser
.Parse( s
, s
+ m_Contents
[i
].length() );
251 pFCtx
->m_FileName
= m_Files
[i
];
257 void spInterFileContext::WriteToFiles()
259 for( size_t i
= 0; i
!= m_Files
.size(); ++i
)
261 FILE* fp
= fopen( m_Files
[i
].c_str(), "w+t" );
265 fwrite( m_Contents
[i
].c_str(), sizeof(char), m_Contents
[i
].length(), fp
);
272 wxString
spInterFileContext::GetBody( spContext
* pCtx
)
274 wxASSERT( pCtx
->PositionIsKnown() ); // DBG:: should be checked by-user code
276 wxString
& source
= m_Contents
[ GetFileNoOfContext( *pCtx
) ];
278 return wxString( source
.c_str() + pCtx
->mSrcOffset
, pCtx
->mContextLength
);
281 wxString
spInterFileContext::GetHeader( spContext
* pCtx
)
283 wxASSERT( pCtx
->PositionIsKnown() ); // DBG:: should be checked by-user code
285 wxASSERT( pCtx
->mHeaderLength
!= -1 ); // DBG:: -/-
287 wxString
& source
= m_Contents
[ GetFileNoOfContext( *pCtx
) ];
289 return wxString( source
.c_str() + pCtx
->mSrcOffset
, pCtx
->mHeaderLength
);