In JavaFX 1.2, Control extended CustomNode then we could override the create function to customize an existing component.
With JavaFX 1.3, Control now extends Parent directly then we do not have any more the create function and my custom component doesn’t compile any more … (because I used the create function to customize my components)
Then, to customize an existing component in JavaFX 1.3, I tried another way
I use the initBlock to create the nodes that I want to add to the existing component to customize it
and then I add these nodes to the children sequence of the existing component.
...
init {
var g = Group {
content: [
Group {
...
content: [
Circle {
...
}
Rectangle {
....
}
...
]
...
]
}
insert g into children;
}
... Now, I have a problem with the css, I want to have a default css for my SearchTextBox which is loaded by default by my component (not in the Scene by the developer) and which can be overridden by the developer.
If you have a solution, please let me know!
This example works on: Windows (Seven), Linux (Ubuntu 10.04) and Mac OS X (10.6.3) with the Default toolkit and the Prism toolkit (JVM argument: -Xtoolkit prism) but there is one bug when you run it as an applet on Mac OS X.
The button have a wrong size, the text is too long….

[update August 8, 2010]this issue is fixed in JavaFX 1.3.1
package customcomponent;
import javafx.scene.Group;
import javafx.scene.paint.Color;
import javafx.scene.shape.Circle;
import javafx.scene.shape.Rectangle;
import javafx.scene.input.MouseEvent;
import javafx.scene.control.TextBox;
import javafx.scene.input.KeyEvent;
public class SearchTextBox extends TextBox {
public var onResetSearch: function(): Void;
public var onSearch: function(s: String): Void;
override var style = "-fx-padding: 0 16 0 0; ";
override var onKeyTyped = function(event:KeyEvent){
if (this.rawText!=""){
onSearch(this.rawText);
}else{
onResetSearch();
}
}
init {
var g = Group {
content: [
Group {
var crossWidth = bind this.layoutBounds.height * 0.45;
var crossHeight = bind this.layoutBounds.height * 0.05;
visible: bind this.rawText.length() > 0
layoutX: bind this.layoutBounds.width - (this.layoutBounds.height / 2.0)
layoutY: bind this.layoutBounds.height / 2.0
content: [
Circle {
fill: Color.GRAY
radius: bind this.layoutBounds.height * 0.325
}
Rectangle {
width: bind crossWidth
height: bind crossHeight
translateX: bind 0 - crossWidth / 2.0
translateY: bind 0 - crossHeight / 2.0
fill: Color.WHITE
rotate: 45
}
Rectangle {
width: bind crossWidth
height: bind crossHeight
translateX: bind 0 - crossWidth / 2.0
translateY: bind 0 - crossHeight / 2.0
fill: Color.WHITE
rotate: -45
}
]
onMouseClicked: function (event: MouseEvent) {
this.commit();
this.text = "";
onResetSearch();
}
}
]
}
insert g into children;
}
}
package searchtextbox;
import javafx.stage.Stage;
import javafx.scene.Scene;
import javafx.scene.text.Text;
import javafx.scene.text.Font;
import javafx.scene.control.Button;
import javafx.scene.control.RadioButton;
import javafx.scene.control.ToggleGroup;
import customcomponent.SearchTextBox;
class ExtRadioButton extends RadioButton {
public var action:function();
override public var selected on replace {
if (selected) {
action();
}
}
}
def macStyleSheet="{__DIR__}resources/mac.css";
def defaultStyleSheet = "/customcomponent/stbcaspian.css";
var stylesheets:String = macStyleSheet;
Stage {
title: "Application title"
width: 250
height: 200
var cssToggleGroup = ToggleGroup {};
scene: Scene {
stylesheets : bind stylesheets
content: [
Text {
font : Font {
size : 16
}
x: 10
y: 30
content: "Search "
}
SearchTextBox {
styleClass : "searchTextBox"
translateX :10
translateY :40
onResetSearch:function(){
println("reset !");
}
onSearch:function(s: String){
println("Search of : {s}");
}
}
Button {
text: "just a button to change focus"
translateX :10
translateY :80
action: function() {
println("Hello !")
}
}
ExtRadioButton {
text: "use the default CSS"
translateX :10
translateY :110
toggleGroup: cssToggleGroup
action: function() {
stylesheets = defaultStyleSheet;
}
}
ExtRadioButton {
text: "use the mac CSS"
translateX :10
translateY :130
toggleGroup: cssToggleGroup
selected: true
action: function() {
stylesheets = macStyleSheet;
}
}
]
}
}