Recommended Posts

Hi!

I'm doing a thing in pixi (actually, in it's dart port (https://github.com/FedeOmoto/pixi) but that should be the same for the purpose of this question) and I'm using its text features (http://www.goodboydigital.com/text-updates/).

I understand that before rendering a text, you set the style in which to render it, and that the style includes many different things like color, align and font... What I don't get is: where do the fonts come from? In the provided example, they used 'Arial' font and I know for sure that you can use 'Snippet' font as well. Is there any list of all available fonts I can choose from? And will these fonts work the on every machine?

 

Share this post


Link to post
Share on other sites

The fonts are whatever fonts the user viewing your page has installed on their system. It's basically the same requirements as using a font on a webpage, and if you use something like Google Fonts you can use their JavaScript API to let pixi know when the font is loaded so it can be used correctly.

Share this post


Link to post
Share on other sites

Hi!

 

Basically Pixi supports 3 kind of fonts: native (the ones provided by your OS), Web Fonts, and Bitmap Fonts.

 

If you take a look at this example: https://github.com/FedeOmoto/pixi_examples/blob/master/web/10_text/index.dart

you'll see that it displays text using four different fonts: Snippet, Podkova, Arvo (Google Web Fonts) and Desyrel (Bitmap Font).

 

The Desyrel font is loaded through the AssetLoader (desyrel.fnt file, that "describes" each character from a .png file), and the Google fonts are loaded via the Dart-JS interop functionality (please take a look at the https://github.com/FedeOmoto/pixi_examples/blob/master/web/10_text/index.html file where the webfont.js script is included).

 

Regarding native fonts, here's a list of "safe" fonts you can use: http://www.w3schools.com/cssref/css_websafe_fonts.asp

Please be aware that using a particular native font is only possible if it's provided by the system browsing your page, for example, I'm using a linux distro that doesn't include an Arial font, so when I hit a page that displays text using Arial, my browser uses a "fallback" font with similar/compatible characteristics.

 

Hope that helps!

Share this post


Link to post
Share on other sites

Exactly, that's the idea!  :)

 

You've to specify which fonts are you going to use like in the example:

  var jsMap = new JsObject.jsify({    'google': {      'families': ['Snippet', 'Arvo:700italic', 'Podkova:700']    },    'active': textDemo.init  });

(Please note that when the web fonts finish loading, your textDemo.init method will be called).

And then, just call the load method of the WebFont JS object using the previously created map like this:
 
  context['WebFont'].callMethod('load', [jsMap]);
And that's it! Snippet, Arvo and Podkova web fonts ready to be used with the Text class  :D

Share this post


Link to post
Share on other sites

Hi there. I am just trying to implement a Google web font into my project. The API docs do not seem to explain this feature at all, so I had to collect bits and pieces from all over the web to get more info on how to use webfonts with Pixi V3.

 

But there are some strange things that really confuse me...

 

First, it seems to work without that WebFont.js script. I am just loading a web font like this:

PIXI.loader	.add ("Font1", "http://fonts.googleapis.com/css?family=Yanone+Kaffeesatz&text=ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789")	.on  ("progress", function() {console.log("LOADING...")} )	.once("complete", titleScreen )	.load();					

And in my titleScreen() function I create a text using this font:

var TxtTitle = new PIXI.Text("Some example text here",	{	font: "80px Yanone Kaffeesatz",	align: "center",	x: gameW/2,	y: gameH/2,	});Stage.addChild(TxtTitle);

This seems to work, but the strange thing is, the correct font is NOT displayed the first time (when it has to be loaded). Instead, the text is printed using some native font.

 

When I refresh the game page, the text suddenly shows with the loaded font face.

 

So I guess the loader does not work correctly with web fonts and can't detect whether a web font is loaded or not. It just says "okay, everything finished" and calls my load complete function.

 

When I refresh the game page, the web font already seems cached by the browser and is therefore available.

 

Can someone confirm this? Or let me know what I am doing wrong?

 

Share this post


Link to post
Share on other sites

 

 

The API docs do not seem to explain this feature at all, so I had to collect bits and pieces from all over the web to get more info on how to use webfonts with Pixi V3.1

 

Webfonts are supported by your browser and therefore pixi.js. Pixi does no special handling for fonts.

 

 

 

 I am just loading a web font like this:

 

You probably don't want to do that, the Pixi loader isn't built for loading fonts. There are a lot of weird behaviors trying to load them, use a tool specifically built for it like font loader. Or just use CSS.

 

 

This seems to work, but the strange thing is, the correct font is NOT displayed the first time (when it has to be loaded). Instead, the text is printed using some native font.

 

When I refresh the game page, the text suddenly shows with the loaded font face.

 

See: browser caching. The first time you are drawing with the font before the browser loads it, the second time it is cached and loads instantly.

 

 

 

So I guess the loader does not work correctly with web fonts and can't detect whether a web font is loaded or not. It just says "okay, everything finished" and calls my load complete function.

 

The loader just loads data and presents it to you, downloading the font via XHR means nothing for it actually being used. Don't use the resource-loader for this.

Share this post


Link to post
Share on other sites

You should point this out in the docs then, otherwise the user has to guess what's going on. Unfortunately, the docs are more then rudimentary at the moment. I had (and still have) to search all kind of bits together from various sources. And most sources are still v2 or even v1 related. This is quite frustrating and time consuming :-(

Share this post


Link to post
Share on other sites

BTW: How do I change / update a bitmaptext's text?

 

According to the docs, bitmaptexts provide a .setText() method, but it is stated as deprecated.

 

The only hint there reads "see PIXI.BitmapText#text" -which is a broken link and leads to nowhere  :blink: 

 

EDIT: Solved -the console warning said I should use .text = instead. This property is not shown in the docs, however.

Share this post


Link to post
Share on other sites

BTW: How do I change / update a bitmaptext's text?

 

According to the docs, bitmaptexts provide a .setText() method, but it is stated as deprecated.

 

The only hint there reads "see PIXI.BitmapText#text" -which is a broken link and leads to nowhere  :blink: 

 

EDIT: Solved -the console warning said I should use .text = instead. This property is not shown in the docs, however.

 

I fixed the docs, should be updated on the website soon.

Share this post


Link to post
Share on other sites
On 8/26/2015 at 10:52 PM, xerver said:

See: browser caching. The first time you are drawing with the font before the browser loads it, the second time it is cached and loads instantly.

I am seeing a similar issue where when you refresh the page, Sometimes the font is loaded and other times it isnt. I have the google font loaded in the HTML. I created a div to test the font as well as a pixi scrolling font, which I need for the project. The weird thing is the font doesn't load at all unless the div I created is present. So... problem 1: unreliable font and problem 2: dependent on an unneeded div.

<!doctype html>
<title>Hello World</title>
<head>
<link rel="stylesheet" type="text/css" href="https://fonts.googleapis.com/css?family=Oswald" />
<link rel="stylesheet" type="text/css" href="css/main.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/pixi.js/4.2.3/pixi.js"></script>
</head>
<body>
	<div>font should work</div>
    <script src="scripts/main.js"></script>
</body>

css:

div {
  font: 24px 'Oswald';
  visibility: hidden;
}

js:

//Aliases: this is shorthand
var Container = PIXI.Container,
  autoDetectRenderer = PIXI.autoDetectRenderer,
  loader = PIXI.loader,
  resources = PIXI.loader.resources,
  Sprite = PIXI.Sprite;

//Create a Pixi stage and renderer and add the 
//renderer.view to the DOM
var interactive = true;
var stage = new Container(interactive),
  renderer = autoDetectRenderer(500, 500, {
    antialias: false,
    transparent: false,
    resolution: 1
  });
document.body.appendChild(renderer.view);


var btbTexture = PIXI.Texture.fromImage('https://res.cloudinary.com/dubyisimd/image/upload/v1481228417/buttonplaceholder_iit0dp.png');
var btn = new PIXI.Sprite(btbTexture);
btn.anchor.x = 0.5;
btn.anchor.y = 0.5;
btn.position.x = renderer.width / 2;
btn.position.y = renderer.height / 2;
btn.interactive = true;
btn.on('mousedown', () => console.log('mousedown'));
stage.addChild(btn);



//load an image and run the `setup` function when it's done
loader
//add the font you want to use below:
//  .add("Oswald", "https://fonts.googleapis.com/css?family=Oswald")
//also add images by:
//.add("images/beerCup_logo.png")
  .add("https://res.cloudinary.com/dubyisimd/image/upload/v1481228417/buttonplaceholder_iit0dp.png")
  //creates a progress statement that will check to see if assets are loading
  .on("progress", loadProgressHandler)
  .load(ScrollingText, addButton);
//.load();

//this function will check to see if all assets are loading to the stage. loader 
function loadProgressHandler(loader, resource) {
  //Display the file `url` currently being loaded
  console.log("loading: " + resource.url);

  //Display the precentage of files currently loaded
  console.log("progress: " + loader.progress + "%");

  //If you gave your files names as the first argument 
  //of the `add` method, you can access them like this
  //console.log("loading: " + resource.name); 
}
//button:
function addButton() {

  button = new sprite(resources["https://res.cloudinary.com/dubyisimd/image/upload/v1481228417/buttonplaceholder_iit0dp.png"].texture);
  stage.addChild(button);

  button.x = 15;
  button.y = 15;

}

//text scroll:
function ScrollingText() {

  text = new PIXI.Text('This is a pixi text', {
    fontFamily: 'Oswald',
    fontSize: 24,
    fill: 0xff1010,
    align: 'center'
  });

  stage.addChild(text);

  text.x = 500;
  text.y = 0;

  gameLoop();
}

function gameLoop() {
  requestAnimationFrame(gameLoop);

  text.x -= 1;

  renderer.render(stage);
}

 

Share this post


Link to post
Share on other sites

I put together an example of using a Google Web Font which seems to work reliably.

Here is a demo:
http://commins.ca/pixijs-web-font-example/

Here is the code:

<!DOCTYPE html>
<html>
<head>
    <title>PixiJS Web Font Example</title>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/pixi.js/4.2.3/pixi.js"></script>
    <script src="https://ajax.googleapis.com/ajax/libs/webfont/1.6.26/webfont.js"></script>
    <script>
    // https://github.com/typekit/webfontloader
    fontsLoaded = false;
    WebFont.load({
        google: {
            families: ['Noto Sans']
        },
        loading: function() { console.log('Font(s) Loading'); },
        active: function() { console.log('Font(s) Loaded'); fontsLoaded = true; },
        inactive: function() { console.log('Font(s) Failure'); }
    });
    </script>
</head>
<body>
    <script type="text/javascript">
        var renderer = PIXI.autoDetectRenderer(640, 128);
        document.body.appendChild(renderer.view);

        // create the root of the scene graph
        var stage = new PIXI.Container();

        // PIXI.loader
        //     .add("image1.png")
        //     .add("image2.png")
        //     .add("image3.png")
        //     .load(setup);

        // calling setup directly because we do not actually need any images, etc.
        setup();

        function setup() {
            var intervalId;
            intervalId = setInterval(() => {
                if(fontsLoaded) {
                    text = new PIXI.Text('The quick brown fox jumps over the lazy dog', {
                        fontFamily: 'Noto Sans',
                        fontSize: 24,
                        fill: 0xffffff
                    });
                    stage.addChild(text);
                    text.x = renderer.view.width/2;
                    text.y = renderer.view.height/2;
                    text.anchor.set(0.5);
                    renderer.render(stage);
                    clearInterval(intervalId);
                }
            }, 20);
        }
    </script>
</body>
</html>

 

Share this post


Link to post
Share on other sites
Quote

I put together an example of using Google Web Font which seems to work reliably.

This method, with the set interval, is called polling and its generally a fallback for when other methods do not work as its wasteful to repeatedly call a function when you don't need to. Seeing as the WebfontLoader uses callbacks you don't need to poll, just fire whatever function you like when the fonts have loaded (its been a while since I dug in to webfont loader but its entirely possible it uses polling itself to avoid errant load events, but you have no such concerns about its callbacks getting fired).

As you're loading the font in the head (which is a good idea when possible) in the 'active' callback you'd want to make sure that the setup function you want to fire exists already to deal with the case that the fonts load before your script. This way results in your setup function getting called a max of 3 times whereas polling with a 20ms gap means it'll get called roughly 50 times per second and depending on your connection you could be waiting a bit for fonts. If the fonts do indeed load before your setup function is declared then thats cool because now you'll only call it twice (once explicitly and once from the image loader).

In this example its fairly terse but ditching polling when possible is something to consider.

Share this post


Link to post
Share on other sites

I know this is an old topic, but for future reference, I managed to solve this in a fairly simple yet alternative way if you're bundling your project together and don't want to include another .js file from CDN inside your HTML (in my case, my whole app is a single .js file, for optimization).

1. Install webfontloader from npm (this is the same as Google's WebFont):

npm install webfontloader --save

1.1. If you're using TypeScript, you can also install its types

npm install @types/webfontloader --save

2. Add your fonts to your HTML wrapper. In my case I had custom .woff fonts so I copied them to my destination asset folder and had them straight in the HTML:

<!doctype html>
<html lang="en">
<head>
	<meta charset="utf-8">

	<!-- Metadata: main -->
	<title><%= htmlWebpackPlugin.options.title %></title>

	<!-- Styles -->
	<style>
		body {
			margin: 0;
			padding: 0;
			background: #999999;
			overflow: scroll;
		}
		/* n2 */
		@font-face {
			font-family: 'My Font Name';
			font-style: light;
			font-weight: 200;
			src: local('My Font Name Light'), local('My-Font-Name-Light'), url(fonts/MyFontName-Light.woff) format('woff');
		}
		/* n4 */
		@font-face {
			font-family: 'My Font Name';
			font-style: normal;
			font-weight: 400;
			src: local('My Font Name Regular'), local('My-Font-Name-Regular'), url(fonts/MyFontName-Regular.woff) format('woff');
		}
		/* n7 */
		@font-face {
			font-family: 'My Font Name';
			font-style: bold;
			font-weight: 700;
			src: local('My Font Name Bold'), local('My-Font-Name-Bold'), url(fonts/MyFontName-Bold.woff) format('woff');
		}
	</style>

	<!-- Metadata: mobile devices -->
	<meta name="viewport" content="width=device-width, height=device-height, initial-scale=1.0, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
</head>

<body>
	<div id="app-container"></div>
<% for (var chunk in htmlWebpackPlugin.files.chunks) { %>	<script defer type="text/javascript" src="<%= htmlWebpackPlugin.files.chunks[chunk].entry %>"></script>
<% } %></body>
</html>

3. Load them inside the index.js file that starts Pixi. This function does it:

import * as WebFont from "webfontloader";

...

WebFont.load({
	custom: {
		families: [ "My Font Name:n2,n4,n7" ],
	},
	fontactive: (name, fvd) => {
		console.log(`Loading font files ${name}:${fvd}`);
	},
	active: () => {
		console.log("All font files loaded.");
		// CONTINUE here
	},
	inactive: () => {
		console.error("Error loading fonts");
		// REPORT ERROR here
	},
});

In the above code, "active" is the key, as it's the callback for when all fonts have loaded. No need for interval checks.

In my own case the above code was part of a promise that resolve()d inside "active", and reject()ed inside "inactive".

Check webfontloader for more details on loading fronts from vendors, or the "n2/n4/n7" nomenclature standard (again, same as "WebFont").

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...

  • Recently Browsing   0 members

    No registered users viewing this page.