polserver/pol-core/bscript/str.cpp

108 lines
2.2 KiB
C++
Raw Permalink Normal View History

#include "bscript/str.h"
2016-02-11 22:54:43 +01:00
#include "bscript/bdouble.h"
#include "bscript/blong.h"
#include "bscript/bobject.h"
namespace Pol::Bscript
{
void int_to_binstr( int& value, std::stringstream& s )
{
int i;
for ( i = 31; i > 0; i-- )
{
if ( value & ( 1 << i ) )
break;
}
for ( ; i >= 0; i-- )
{
if ( value & ( 1 << i ) )
s << "1";
else
s << "0";
}
}
bool try_to_format( std::stringstream& to_stream, BObjectImp* what, std::string& frmt )
{
if ( frmt.empty() )
{
to_stream << what->getStringRep();
return false;
}
if ( frmt.find( 'b' ) != std::string::npos )
{
if ( auto* plong = impptrIf<BLong>( what ) )
{
int n = plong->value();
if ( frmt.find( '#' ) != std::string::npos )
to_stream << ( ( n < 0 ) ? "-" : "" ) << "0b";
int_to_binstr( n, to_stream );
}
else
{
to_stream << "<needs Int>";
return false;
}
}
else if ( frmt.find( 'x' ) != std::string::npos )
{
if ( auto* plong = impptrIf<BLong>( what ) )
{
int n = plong->value();
if ( frmt.find( '#' ) != std::string::npos )
to_stream << "0x";
to_stream << std::hex << n << std::dec;
}
else
{
to_stream << "<needs Int>";
return false;
}
}
else if ( frmt.find( 'o' ) != std::string::npos )
{
if ( auto* plong = impptrIf<BLong>( what ) )
{
int n = plong->value();
if ( frmt.find( '#' ) != std::string::npos )
to_stream << "0o";
to_stream << std::oct << n << std::dec;
}
else
{
to_stream << "<needs Int>";
return false;
}
}
else if ( frmt.find( 'd' ) != std::string::npos )
{
int n;
if ( auto* plong = impptrIf<BLong>( what ) )
n = plong->value();
else if ( auto* pdbl = impptrIf<Double>( what ) )
n = (int)pdbl->value();
else
{
to_stream << "<needs Int, Double>";
return false;
}
to_stream << std::dec << n;
}
else
{
to_stream << "<bad format: " << frmt << ">";
return false;
}
return true;
}
Add support for interpolated strings ("interstrings") (#369) * Update grammar to support interpolated strings * Struct initializers, case switchs are regular strings * Initial stub for interpolated string in AST This splits the previous STRING_LITERAL terminal into a production, stringLiteral, to handle REGULAR_STRING terminal and interpolatedString production. * Change interpolated strings to expressions * Fix mode handling in grammar * Grammar fixes - Fix mode handling in lexer - Interpolated strings only have one expression * Can successfully parse, stub compile interstrings $"He {there + print("hello")}"; * Add formatting string to grammar * Fix tests, and add test stubs * Rename curleys to brace; better AST generation * initial work interstring instruction * Initial work on formatted string instruction: emit * Formatted string instruction: execution * Add simple formatted string test * Add formatted string test src * Review changes #1 - Rename `FormattedString` to `FormatExpression` - Rename overloaded `try_to_format()` to `get_formatted()` * Review changes part 2 - Rename `InterpolatedString` ast node to `InterpolateString` * Review changes part 3 - Modify `ins_interpolate_string` * Review changes part 4 - Remove unused formal parameter * Add negative tests * Spruce up positive tests * Fix braces, escape chars inside interstring * Fix, add tests for escaped char and double brace * Address differences for new lines in tests * Update Escript version * Make empty expression an error * Add documentation for interpolated strings * Quick touchup on docs
2021-03-11 22:48:16 +01:00
std::string get_formatted( BObjectImp* what, std::string& frmt )
{
std::stringstream result;
try_to_format( result, what, frmt );
return result.str();
}
} // namespace Pol::Bscript