ZioByte ZioByte - 1 year ago 63
CSS Question

In JavaFX 8 can I provide a stylesheet from a String?

Is it possible to wrap a whole Stylesheet in a string and apply it to a certain node?
Usage case would be to add specific (non changeble) behavior for PseudoClass.
I know I can use

, but I would like to know if there's some way to embrd it direcly in source; something along the lines:

".button:ok { -fx-background-color: green; }\n"+
".button:ko { -fx-background-color: red; }");

Answer Source

I found a way of doing this by defining a new URL connection:

private String css;

public void initialize() {
    // to be done only once.
    URL.setURLStreamHandlerFactory(new StringURLStreamHandlerFactory());

private void updateCss(Node node) {
    // can be done multiple times.
    css = createCSS();

private class StringURLConnection extends URLConnection {
    public StringURLConnection(URL url){

    @Override public void connect() throws IOException {}

    @Override public InputStream getInputStream() throws IOException {
        return new StringBufferInputStream(css);

private class StringURLStreamHandlerFactory implements URLStreamHandlerFactory {
    URLStreamHandler streamHandler = new URLStreamHandler(){
        @Override protected URLConnection openConnection(URL url) throws IOException {
            if (url.toString().toLowerCase().endsWith(".css")) {
                return new StringURLConnection(url);
            throw new FileNotFoundException();
    @Override public URLStreamHandler createURLStreamHandler(String protocol) {
        if ("internal".equals(protocol)) {
            return streamHandler;
        return null;

Obviously protocol "internal" can be any (non clashing) well-formed string and (in this simple example) filepath is compeltely ignored.

I use this to set the global .css, so I do not need to remember multiple strings. It seems the Stream is opened just once, but I do not know if this holds true in all cases.

Feel free to complicate the code as needed ;)

Credit for this method goes to Jasper Potts (see this example)