1 /////////////////////////////////////////////////////////////////////////////
3 // Purpose: Contrib. demo
4 // Author: Aleksandras Gluchovas
8 // Copyright: (c) Aleksandars Gluchovas
9 // Licence: GNU General Public License
10 /////////////////////////////////////////////////////////////////////////////
12 // This program is free software; you can redistribute it and/or modify
13 // it under the terms of the GNU General Public License as published by
14 // the Free Software Foundation; either version 2 of the License, or
15 // (at your option) any later version.
17 // This program is distributed in the hope that it will be useful,
18 // but WITHOUT ANY WARRANTY; without even the implied warranty of
19 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 // GNU General Public License for more details.
22 // You should have received a copy of the GNU General Public License
23 // along with this program; if not, write to the Free Software
24 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
25 /////////////////////////////////////////////////////////////////////////////
28 // For compilers that support precompilation, includes "wx/wx.h".
29 #include "wx/wxprec.h"
41 #if defined( wxUSE_TEMPLATE_STL )
51 #include "sourcepainter.h"
53 const int MAX_KEYWORD_LEN
= 16;
57 char keyWord
[MAX_KEYWORD_LEN
];
61 // source fragment ranks :
67 // multil-language keywords map
69 static KeywordT __gKeyWords
[] =
141 ////////////////////////////////////////////////////
175 ////////////////////////////////////////////////////
177 { "dynamic_cast", 1 },
180 //////// some hacks for VB /////////
189 /////// data types ///////
270 { "throw", 2 }, // C++
271 { "throws", 1 }, // Java
289 //////////// meta-information //////////////
320 { "implementation", 2 },
321 { "Implementation", 2 },
322 { "IMPLEMENTATION", 2 },
380 { "[ag_slammer]",2 },
381 { "Aleksandras", 2 },
398 inline bool operator()( char* x
, char* y
) const
399 { return ( strcmp( x
,y
) < 0 );
403 #if defined( wxUSE_TEMPLATE_STL )
405 typedef map
< char*, char*, less_c_str
> KeywordMapT
;
409 typedef char* CharPtrT
;
410 typedef WXSTL_MAP( CharPtrT
, CharPtrT
,less_c_str
) KeywordMapT
;
414 static KeywordMapT __gMultiLangMap
;
415 static int __gMapReady
= 0;
417 void check_keyword_map( int keywordMapNr
)
423 // "make sure" the address of the first member of non-polimorphic class
424 // coinsides with the address of the instance
428 if ( (char*)& dummy
!= &dummy
.keyWord
[0] )
431 int size
= sizeof(__gKeyWords
) / sizeof( KeywordT
);
433 for( int i
= 0; i
!= size
; ++i
)
435 __gMultiLangMap
.insert(
436 KeywordMapT::value_type( (char*)&__gKeyWords
[i
],
437 (char*)&__gKeyWords
[i
]
443 int get_rank( char* start
, char* end
)
445 // FIXME:: what if end is no longer leagal adress?
448 *end
= '\0'; // put temporary terminator
450 KeywordMapT::iterator i
;
452 if ( (i
= __gMultiLangMap
.find( start
) ) != __gMultiLangMap
.end() )
454 KeywordT
* pKey
= (KeywordT
*)(*i
).second
;
467 static inline void store_range( IntListT
& results
, int rank
, int range_len
)
469 if ( !range_len
) return;
471 results
.push_back ( ( rank
<< 16 ) | ( range_len
) );
475 #define STORE_RANGE store_range( results, cur_rank, cur_range_len );\
476 cur_rank = cur_range_len = 0;
478 #define NEXT_CHAR cur_range_len++; \
482 static inline int is_alpha( char ch
)
484 return ( (( ch
>= '_' ) && ( ch
<= 'z' )) ||
485 (( ch
>= 'A' ) && ( ch
<= 'Z' ))
490 // Ziema atEjo netikEtai
492 static void heighlight_syntax( char* str
, int strLen
,
493 IntListT
& results
, bool& isComment
)
495 bool isMultiline
= 0;
497 char* end
= str
+ strLen
;
499 int cur_rank
= ( isComment
== 1 ) ? RANK_GREEN
: RANK_BLACK
;
500 int cur_range_len
= 0;
504 int has_next
= ( cur
+1 != end
);
509 if ( has_next
&& *(cur
+1) == '/' )
511 // turn off multiline comment mode
531 cur_rank = RANK_GREEN;
532 cur_range_len = end - cur;
543 if ( *(cur
+1) == '/' )
548 while ( eol
< end
&& *eol
!= 10 )
551 cur_rank
= RANK_GREEN
;
552 cur_range_len
= eol
- cur
;
559 if ( *(cur
+1) == '*' )
562 cur_rank
= RANK_GREEN
;
574 if ( ( is_alpha( *cur
) || *(cur
) == '#' )
578 if ( is_alpha( *(cur
+1) ) )
583 while ( cur
!= end
&& is_alpha(*cur
) ) ++cur
;
587 if ( (wordRank
= get_rank( start
, cur
)) > 0 )
591 store_range( results
, wordRank
, int(cur
-start
) );
592 cur_rank
= cur_range_len
= 0;
596 cur_range_len
+= ( cur
-start
);
606 if ( cur_range_len
> 0 ) STORE_RANGE
;
609 /***** Implementation for class SourcePainter ******/
611 SourcePainter::SourcePainter( bool assembleResultString
)
612 : mCollectResultsOn( assembleResultString
),
613 mIsInComment( FALSE
),
614 mCommentIsMultiline( FALSE
)
616 check_keyword_map(0);
619 void SourcePainter::ProcessSource( char* src
, int srcLen
)
621 // TBD:: multilne state...
623 heighlight_syntax( src
, srcLen
, mBlocks
, mIsInComment
);
625 if ( mCollectResultsOn
)
627 mResultStr
+= string( src
, srcLen
);
630 void SourcePainter::SetState( bool isInComment
,
631 bool commentIsMultiline
)
633 mIsInComment
= isInComment
;
634 mCommentIsMultiline
= commentIsMultiline
;
637 void SourcePainter::Init(bool assembleResultString
)
640 mCommentIsMultiline
= 0;
641 mCollectResultsOn
= assembleResultString
;
645 mBlocks
.erase( mBlocks
.begin(), mBlocks
.end() );
648 static int rank_tags_map
[] =
656 void SourcePainter::GetResultString(string
& result
, MarkupTagsT tags
)
658 // this method works, only if results of processing
660 ASSERT( mCollectResultsOn
);
665 for( size_t i
= 0; i
!= mBlocks
.size(); ++i
)
667 int desc
= mBlocks
[i
];
669 int len
= desc
& 0xFFFF;
670 int rank
= (desc
>> 16) & 0xFFFF;
672 result
+= tags
[ rank_tags_map
[rank
] ].start
;
674 for( int n
= 0; n
!= len
; ++n
)
676 result
+= mResultStr
[pos
+n
];
680 result
+= tags
[ rank_tags_map
[rank
] ].end
;
684 IntListT
& SourcePainter::GetBlocks()
689 bool SourcePainter::IsKeyword( char* word
, int wordLen
)
691 check_keyword_map(0);
693 int rank
= get_rank( word
, word
+ wordLen
);
695 return ( rank
== RANK_BLUE
|| rank
== RANK_RED
);