vtex2 icon indicating copy to clipboard operation
vtex2 copied to clipboard

worldtext font atlas creation

Open JJL772 opened this issue 3 years ago • 1 comments

Hammer and in-game world text entities use a basic font atlas to draw fonts in game. vtex2 should add an action to generate a font atlas from a .ttf or .otf file.

worldtextsheet.vtf looks like this for example: image

JJL772 avatar Jul 19 '22 23:07 JJL772

I have code for this for the GUI, TTF and OTF. this is only because QT is quite excellent at rasterizing fonts. Trust me, this took me longer than I'd like to admit.

	int id = QFontDatabase::addApplicationFont( filepath );
	QString family = QFontDatabase::applicationFontFamilies( id ).at( 0 );
	QString charList = R"( !"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|})";

	QTextOption opts;

	QBuffer buff;
	QImage image( QSize( 1024, 1024 ), QImage::Format_RGBA8888 );

	QPainter painter;
	painter.begin( &image );
	// This fixes a weird issue where background will become garbage data
	// if not cleared first. 
	painter.setCompositionMode( QPainter::CompositionMode_Source );
	painter.fillRect( QRect( 0, 0, 1024, 1024 ), QColor( 0, 0, 0, 0 ) );
	painter.setCompositionMode( QPainter::CompositionMode_SourceOver );
	painter.setBrush( Qt::transparent );
	painter.setPen( QPen( Qt::white ) );
	auto font = QFont( family );
	auto offset = 32;
	font.setPointSize( offset );
	painter.setFont( font );

	//	painter.drawRect( 0, 0, 1024, 1024 );
	for ( int i = 0, j = 0, k = 0; k < charList.length(); i++, k++ )
	{
		if ( i > 15 )
		{
			j++;
			i = 0;
		}
		painter.drawText( ( i * 64 ) + offset / 2, ( j * 64 ) + offset * 1.5, charList[k] );
	}
	painter.end();

	QByteArray im;
	QBuffer bufferrgb( &im );
	bufferrgb.open( QIODevice::WriteOnly );

	image.save( &bufferrgb, "PNG" );

	int x, y, n;

	stbi_uc *data = stbi_load_from_memory( reinterpret_cast<const stbi_uc *>( bufferrgb.data().constData() ), bufferrgb.size(), &x, &y, &n, 4 );
	QFontDatabase::removeApplicationFont( id );

For the CLI it'd be really difficult unless the CLI becomes a QT application itself.

Trico-Everfire avatar Mar 17 '24 22:03 Trico-Everfire