Is there any way to reference a custom javascript function from BEML? I'd like to keep away from Flash since what ever I do needs to work in the HTML5 player as well.
<Runtime>
<Layout width="800" height="600" id="backgroundTemplate">
<Canvas>
<VideoDisplay id="videoPlayer" width="788" height="487" x="9" y="13"/>
<MediaControls x="5" y="509" width="791" height="87" id="mediaControls">
<VBox>
<Canvas height="25" padding="20">
<Playhead mediaController="{videoPlayer}" autohideSlider="false" useTimeToolTip="true"/>
</Canvas>
<HBox padding="10">
<HBox id="leftBtn_container" hAlign="left">
<ToggleButton id="playButton" width="60" height="60" x="0" y="0" showBack="true" click="{videoPlayer.play()}" toggledClick="{videoPlayer.pause()}" toggled="{videoPlayer.playing}"/>
</HBox>
<HBox id="rightBtn_container" hAlign="right">
<Button width="60" height="60" id="cite_btn" click="{someFunction.doSomething()}"/>
</HBox>
</HBox>
</VBox>
</MediaControls>
</Canvas>
</Layout>
</Runtime>
You would need to create a custom component.Creating Custom Player Components
Call custom component in BEML.
<Modules>
<Module file="http://urltocustomcomponent.com/my_component.swf" />
</Modules>
Button in BEML
<ToggleButton id="my_button" width="40" height="40" />
Actionscript for custom component.
package
{
import com.brightcove.api.APIModules;
import com.brightcove.api.BrightcoveModuleWrapper
import com.brightcove.api.CustomModule;
import com.brightcove.api.modules.ExperienceModule;
import com.brightcove.api.events.BEMLMouseEvent;
import flash.events.Event;
import flash.external.ExternalInterface;
import com.brightcove.api.components.Button;
public class yogaComponent extends CustomModule
{
override protected function initialize():void
{
// Get the experience module
var experienceModule:ExperienceModule = player.getModule(APIModules.EXPERIENCE) as ExperienceModule;
// Define Info Button
var button:Button = experienceModule.getElementByID("my_button") as Button;
// Our listener that calls the function
button.addEventListener(BEMLMouseEvent.CLICK, myCustomFunc);
}
// Custom Function
private function myCustomFunc(event:Event):void
{
if(ExternalInterface.available)
{
// this calls a javascript function in your html
ExternalInterface.call('myJavascriptAlertFunction');
}
}
}
}
Javascript function that is called on event click.
function myJavascriptAlertFunction()
{
alert('it works!');
}
Related
I haven't been able to find info on this, but I've created a layout in Scene Builder, and I've placed an AnchorPane inside an empty ScrollPane, and added text, a slider, and a label in rows, and then added a button for the user to add a new entry of the above.
Basically a typical preference elicitation UI where the user can also add new entries and specify their own preference values as well.
When pressed, for testing purposes, the button creates a new label, adds it to the AnchorPane, and relocates it to a Y position outside the AnchorPane, and then resizes the AnchorPane so that the new label is included.
The problem that I'm having is that the ScrollPane doesn't adjust and expand the scrollable area to fit the new AnchorPane height, so I can't scroll down to where the new label is visible. In Scene Builder, on the other hand, if I resize the AnchorPane so that it's larger than the ScrollPane, the latter dynamically adjusts the scrollable area, so I'm not sure what the problem is.
Any help is appreciated.
EDIT:
As requested, below is a minimally reproducible version of the project.
Class that loads the FXML and creates the scene
package main;
import java.io.IOException;
import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Scene;
import javafx.scene.control.TitledPane;
import javafx.stage.Stage;
public class Registration_Page extends Application {
private Stage primaryStage;
private TitledPane mainLayout;
#Override
public void start(Stage primaryStage) throws IOException {
this.primaryStage = primaryStage;
showMainView();
}
private void showMainView() throws IOException {
FXMLLoader loader = new FXMLLoader(Registration_Page.class.getResource("resources/Registration_Page.fxml"));
mainLayout = loader.load();
Scene scene = new Scene(mainLayout);
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args) {
launch(args);
}
}
Class that acts as the button controller, using FXML-defined components.
package main;
import javafx.event.ActionEvent;
import javafx.fxml.FXML;
import javafx.scene.control.Button;
import javafx.scene.control.Label;
import javafx.scene.control.ScrollPane;
import javafx.scene.layout.AnchorPane;
public class ButtonController {
#FXML
private Button plus;
#FXML
private AnchorPane prefValuesAnchorPane;
#FXML
private ScrollPane scrollPane;
#FXML
protected void plusAction(ActionEvent event) {
Label lbl1 = new Label("Hello");
prefValuesAnchorPane.getChildren().add(lbl1);
lbl1.relocate(18, 250);
System.out.println(prefValuesAnchorPane.getHeight());
System.out.println(lbl1.getLayoutY());
if (lbl1.getLayoutY() >= prefValuesAnchorPane.getHeight())
{
prefValuesAnchorPane.resize(prefValuesAnchorPane.getWidth(), lbl1.getLayoutY() + 3);
}
}
}
The FXML document
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.Button?>
<?import javafx.scene.control.Label?>
<?import javafx.scene.control.ScrollPane?>
<?import javafx.scene.control.Slider?>
<?import javafx.scene.control.TextField?>
<?import javafx.scene.control.TitledPane?>
<?import javafx.scene.layout.AnchorPane?>
<?import javafx.scene.text.Font?>
<?import javafx.scene.text.Text?>
<TitledPane animated="false" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" text="User Registration" xmlns="http://javafx.com/javafx/11.0.1" xmlns:fx="http://javafx.com/fxml/1" fx:controller="main.ButtonController">
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0">
<children>
<TextField layoutX="52.0" layoutY="79.0" />
<Text layoutX="14.0" layoutY="96.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Name" />
<Text layoutX="14.0" layoutY="130.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Preference Values">
<font>
<Font size="14.0" />
</font>
</Text>
<ScrollPane fx:id="scrollPane" layoutX="14.0" layoutY="137.0" prefHeight="223.0" prefWidth="332.0">
<content>
<AnchorPane fx:id="prefValuesAnchorPane" minHeight="0.0" minWidth="0.0" prefHeight="217.0" prefWidth="329.0">
<children>
<Text layoutX="15.0" layoutY="30.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Val1:" />
<Slider blockIncrement="1.0" layoutX="115.0" layoutY="15.0" majorTickUnit="1.0" max="10.0" minorTickCount="0" prefWidth="140.0" showTickLabels="true" snapToPixel="false" snapToTicks="true" />
<Label layoutX="280.0" layoutY="12.0" text="0">
<font>
<Font name="System Bold" size="14.0" />
</font>
</Label>
<Text layoutX="15.0" layoutY="62.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Val2:" />
<Slider blockIncrement="1.0" layoutX="115.0" layoutY="50.0" majorTickUnit="1.0" max="10.0" minorTickCount="0" prefWidth="140.0" showTickLabels="true" snapToTicks="true" />
<Label layoutX="280.0" layoutY="48.0" text="0">
<font>
<Font name="System Bold" size="14.0" />
</font>
</Label>
<Text layoutX="15.0" layoutY="97.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Val3:" />
<Slider blockIncrement="1.0" layoutX="115.0" layoutY="85.0" majorTickUnit="1.0" max="10.0" minorTickCount="0" prefWidth="140.0" showTickLabels="true" snapToTicks="true" />
<Label layoutX="280.0" layoutY="82.0" text="0">
<font>
<Font name="System Bold" size="14.0" />
</font>
</Label>
<Text layoutX="15.0" layoutY="133.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Val4:" />
<Slider blockIncrement="1.0" layoutX="115.0" layoutY="120.0" majorTickUnit="1.0" max="10.0" minorTickCount="0" prefWidth="140.0" showTickLabels="true" snapToTicks="true" />
<Label layoutX="280.0" layoutY="118.0" text="0">
<font>
<Font name="System Bold" size="14.0" />
</font>
</Label>
<Button fx:id="plus" graphicTextGap="1.0" layoutX="289.0" layoutY="153.0" maxHeight="-Infinity" maxWidth="-Infinity" mnemonicParsing="false" onAction="#plusAction" prefHeight="0.0" prefWidth="30.0" text="+" textAlignment="CENTER" textOverrun="CENTER_ELLIPSIS" AnchorPane.topAnchor="153.0">
<font>
<Font name="System Bold" size="14.0" />
</font>
</Button>
</children>
</AnchorPane>
</content>
</ScrollPane>
<Button layoutX="532.0" layoutY="335.0" mnemonicParsing="false" text="Next" />
</children></AnchorPane>
</content>
</TitledPane>
The solution to this is to instead have a ScrollPane containing an AnchorPane (as it was), and for every entry added, create an AnchorPane or BorderPane or any other container pane (afaik), and add whatever to it, rather than adding components such as buttons or labels directly onto the original AP that's attached to the SP.
I have created my view for a JavaFX project using FXML. I was wondering if it's possible to add a few more items to the view pragmatically in controller class?
For example, how can I add another set of Text and TextField in my controller file?
FXML
<AnchorPane prefHeight="400.0" prefWidth="228.0">
<children>
<Text layoutY="10.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Selected User:" GridPane.rowIndex="0" />
<Text layoutY="45.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Username :" GridPane.rowIndex="1" />
<TextField fx:id="username" layoutY="55.0" GridPane.rowIndex="2" />
<Text layoutY="100.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Address :" GridPane.rowIndex="3" />
<TextField fx:id="address" layoutY="110.0" GridPane.rowIndex="4" />
<Text layoutY="155.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Web Page :" GridPane.rowIndex="5" />
<TextField fx:id="WP" layoutY="165.0" GridPane.rowIndex="6" />
<Text layoutY="210.0" strokeType="OUTSIDE" strokeWidth="0.0" text="State :" GridPane.rowIndex="7" />
<Text layoutY="265.0" strokeType="OUTSIDE" strokeWidth="0.0" text="Login Name :" GridPane.rowIndex="9" />
<TextField fx:id="login_Name" layoutY="275.0" GridPane.rowIndex="10" />
<Button fx:id="btnSave" layoutX="50.0" layoutY="320.0" mnemonicParsing="false" onAction="#btnSaveClicked" text="Save" />
<Button fx:id="btnSave" layoutX="35.0" layoutY="365.0" mnemonicParsing="false" onAction="#btnDeleteUserClicked" text="Delete User" />
<Button fx:id="btnAddNew" layoutX="30.0" layoutY="410.0" mnemonicParsing="false" onAction="#btnAddeNewClicked" text="Add New User" />
<TextField fx:id="state" layoutX="-2.0" layoutY="222.0" />
</children>
</AnchorPane>
Adding New Nodes in FXML
I would say, you should always add new nodes to the FXML unless you have a very good reason not to. Adding nodes to FXML is as easy as adding an extra line to the existing FXML.
<AnchorPane prefHeight="400.0" prefWidth="228.0">
<children>
...
<Text fx:id="newText"/>
<TextField fx:id="newTextField"/>
</children>
</AnchorPane>
These new nodes will be reflected in the scene graph instantaneously and you can bind them to the controller using their fx:id's.
Adding New Nodes in Controller
First, you should have a fx:id defined for the AnchorPane in order to access it in the controller.
<AnchorPane fx:id="anchorPane" prefHeight="400.0" prefWidth="228.0">
<children>
...
</children>
</AnchorPane>
You can then define the new controls and add them the to AnchorPane in the controller.
public class MyController implements Initializable {
#FXML
private AnchorPane anchorPane;
...
public void intialize() {
...
Text newText = new Text("Some Text");
TextField newTextField = new TextField();
anchorPane.getChildren().addAll(newText, newTextField);
...
}
}
I used tabbox to create tabbed page. And each tab includes another zul page. I have 1 controller applied to main page.
If I add some action to component on included zul page, on controller class I cant catch it. If I apply controller to my zul then it creates new instance of controller class.
Here is my code.
<zk>
<style src="/resources/css/default.css" />
<window id="Dealer" class="index"
apply="com.i2i.prm.controller.IndexController" width="100%"
height="100%">
<div class="content" >
<tabbox id="tb" width="100%" forward="onSelect=onSelect">
<tabs id="tabs">
<tab id="info" label="INFO" />
<tab id="create" label="CREATE" />
<tab id="edit" label="EDIT" />
</tabs>
<tabpanels>
<tabpanel id="DealerInfo">
<include id="DealerInfoContent" src="View/Dealer/DealerInfo.zul" />
</tabpanel>
<tabpanel id="DealerCreate">
<include id="DealerCreateContent" src="View/Dealer/DealerCreate.zul" />
</tabpanel>
<tabpanel id="DealerEdit">
<include id="DealerEditContent" src="View/Dealer/DealerEdit.zul" />
</tabpanel>
</tabpanels>
</tabbox>
</div>
</window>
</zk>
And dealerEdit.zul
<zk>
<window title="Dealer Edit" >
<grid width="100%" sizedByContent="true">
<columns>
<column label="" />
</columns>
<rows>
<row >
<label value="Name"></label>
<textbox
value="#{DealerController.user.name }">
</textbox>
</row>
<row>
<label value="Surname"></label>
<textbox
value="#{DealerController.user.surname }" forward="onChange=onASD">
</textbox>
</row>
<row>
<label value="Address"></label>
<textbox
value="#{DealerController.user.address }">
</textbox>
</row>
</rows>
</grid>
</window>
</zk>
This is my controller (IndexController.java) class:
public class IndexController extends GenericForwardComposer {
private User user = new User();;
AnnotateDataBinder binder;
Tabbox tb;
#Override
public void doAfterCompose(Component comp) throws Exception {
// TODO Auto-generated method stub
super.doAfterCompose(comp);
comp.setAttribute(comp.getId() + "Controller", this);
binder = new AnnotateDataBinder(comp);
user.setName("Abdul");
user.setSurname("Rezzak");
user.setAddress("Giderken sağda");
binder.loadAll();
}
public IndexController() {
// TODO Auto-generated constructor stub
}
public void onDFG(ForwardEvent event){
System.out.println(this.hashCode());
}
public void onASD(ForwardEvent event){
System.out.println(this.hashCode());
}
public User getUser() {
return user;
}
public void setUser(User user) {
this.user = user;
}
}
remove <window title="Dealer Edit" > from your included page (DealerEdit.zul) as it forms its own IdSpace. Don't forget to remove the closing </window> tag.
change your onASD method name to include your Include component id i.e. onASD$DealerEditContent. It seems Include also form its own IdSpace and forward event does not work across IdSpace
This should work.
UPDATE 1: I just confirmed that Include is an IdSpace owner component as it implements IdSpace interface so this is the only workaround in your case.
UPDATE 2: I found one more easier way to deal with forwarding events across different IdSpace which is to use component Path within ZUML file for specifying target component. For example in your case you can specify page id in main.zul page
<?page id="main" ?>
and while forwarding event in your included page such as DealerEdit.zul page
<textbox forward="onChange=//main/Dealer.onASD" />
Rest of the code will remain the same.
Reference: http://books.zkoss.org/wiki/ZK_Developer%27s_Reference/Event_Handling/Event_Forwarding#Using_component_Path
I can't reach component by id in the included .zul page. I have one main.zul with a controller and I need to get a component in included zul page through the java controller class, but it returns null.
I know the included method creates new id space but is there any way to get this component?
UPDATE
Here is my code:
the main zul page
<?page title="DealerVizard.zul"?>
<?page id="main" ?>
<?taglib uri="http://www.zkoss.org/dsp/web/core" prefix="c"?>
<?init class="org.zkoss.zkplus.databind.AnnotateDataBinderInit" arg0="./Dealer" ?>
<zk>
<style src="/resources/css/default.css" />
<window id="Dealer" class="index"
apply="com.i2i.prm.controller.IndexController">
<div class="content" width="100%">
<tabbox id="tb" forward="onSelect=onSelect">
<tabs id="tabs">
<tab id="info" label="INFO" />
<tab id="create" label="CREATE" />
<tab id="edit" label="EDIT" />
<tab id="test" label="TEST PANEL(LIST BOX)" />
</tabs>
<tabpanels>
<tabpanel id="DealerInfo">
<include id="DealerInfoContent"
src="View/Dealer/DealerInfo.zul" />
</tabpanel>
<tabpanel id="DealerCreate">
<include id="DealerCreateContent"
src="View/Dealer/DealerCreate.zul" />
</tabpanel>
<tabpanel id="DealerEdit">
<include id="DealerEditContent"
src="View/Dealer/DealerEdit.zul" />
</tabpanel>
<tabpanel id="PagingListBox">
<include id="PagingListBoxContent" // Included here
src="View/TEST/PagingListBox.zul" />
</tabpanel>
</tabpanels>
</tabbox>
</div>
</window>
</zk>
PagingListBox.zul (Included page)
<?page id="list" ?>
<zk>
<grid width="100%">
<columns>
<column label="" />
</columns>
<rows>
<row>
<listbox id="listModel" width="100%" height="100%"
visible="true" span="true" pagingPosition="top" rows="20"
selectedItem="#{DealerController.selected}"
model="#{DealerController.userList}"
forward="onSelect=//main/Dealer.onSelect">
<auxhead>
<auxheader colspan="1">
<textbox
value="#{DealerController.searchUser.name}" maxlength="9"
id="searchCO_ID" forward="onChanging=//main/Dealer.onSearch"
width="100%">
</textbox>
</auxheader>
<auxheader colspan="1">
<textbox
value="#{DealerController.searchUser.surname}" maxlength="21"
id="searchMSISDN" forward="onChanging=//main/Dealer.onSearch"
width="100%">
</textbox>
</auxheader>
<auxheader colspan="1">
</auxheader>
</auxhead>
<listhead>
<listheader label="Name"
sort="auto(UPPER(name))" />
<listheader label="Surname"
sort="auto(UPPER(surname))" />
<listheader label="Delete ?" />
</listhead>
<listitem self="#{each=USERLIST}">
<listcell>
<label value="#{USERLIST.user.name}" />
<textbox
value="#{DealerController.tmpUser.name}" visible="false" />
</listcell>
<listcell>
<label value="#{USERLIST.user.surname}" />
<textbox
value="#{DealerController.tmpUser.surname}" visible="false" />
</listcell>
<listcell>
<button label="Update"
forward="onClick=//main/Dealer.onUpdate" visible="false" />
<button image="icons/edit-delete.png"
label="Delete" forward="onClick=//main/Dealer.onDelete"
width="100%" disabled="true" />
<button label="Save"
forward="onClick=//main/Dealer.onSave" visible="false" />
<button label="Cancel"
forward="onClick=//main/Dealer.onCancel" visible="false" />
</listcell>
</listitem>
</listbox>
<paging id="pagingData" pageSize="20" />
</row>
</rows>
</grid>
</zk>
IndexCOntroller.java
public class IndexController extends GenericForwardComposer {
private List<User> userList = new ArrayList<User>() ;
AnnotateDataBinder binder;
Tabbox tb;
Window Dealer;
private int pageCount=0;
#Override
public void doAfterCompose(Component comp) throws Exception {
// TODO Auto-generated method stub
super.doAfterCompose(comp);
comp.setVariable(comp.getId() + "Controller", this, true);
binder = (AnnotateDataBinder) Dealer.getVariable("binder", true);
System.out.println(Path.getComponent("//list/listModel"));
}
public IndexController() {
// TODO Auto-generated constructor stub
}
}
Normally I wouldn't recommend using Path.getComponent() way to access other components as your application code becomes tightly coupled with your component structure in your view page.
In your case you simplest way is to use AbstractComponent#getFellow(String compId) method so for eg.
Include inc = (Include) Dealer.getFellow("PagingListBoxContent");
Listbox listModel = (Listbox) inc.getFellow("listModel");
System.out.println(listModel);
So in future even if you insert any other component in your ZUML page before your listbox your code will still work.
UPDATE: BTW there was an interesting blogpost on this very topic on ZK blog recently
if your include have id, you can use dollar sign to get the inner components
<zk>
<include id="inc" src="test.zul />
</zk>
test.zul
<zk>
<label id="lab1" value="test1" />
</zk>
you can use "inc$lab1" get the label in test.zul
You can access any component in any other id space using zscript or java. if it is on the same page, but different window then (component B in window A):
Path.getComponent("/A/B");
if it is on a different page then (component B in window A on page P):
Path.getComponent("//P/A/B");
You can find documentation here: http://books.zkoss.org/wiki/ZK%20Developer%27s%20Reference/UI%20Composing/ID%20Space
You can add in your IndexController.java:
...
private Include DealerInfoContent;
...
this way you can access the included component within the parent composer.
(I would suggest to use camelCase ids for it, though).
I am using Flash Builder 4 Burrito Preview - builing a Mobile Application. I have a custom component called footer.mxml. That footer has 4 buttons, and one of them has a lable that is bound to cartValue. I am trying to maintain a global variable called cartValue within all views and footer component.
footer.mxml
<s:Group xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
width="100%" height="64" chromeColor="#000000" fontSize="10">
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
<mx:CurrencyFormatter id="currencyFormatter"
currencySymbol="$"
useThousandsSeparator="true"
precision="2" />
</fx:Declarations>
<fx:Script>
<![CDATA[
[Bindable]
public var cartValue:int;
]]>
</fx:Script>
<s:HGroup width="100%" contentBackgroundColor="#000000" paddingBottom="0" paddingLeft="0"
paddingRight="0" paddingTop="0">
<s:Button x="0" y="624.5" width="25%" height="64" label="Account" chromeColor="#2259AA"
enabled="true" fontSize="10" fontWeight="bold" icon="#Embed('assets/user.png')"/>
<s:Button x="121" y="624.5" width="25%" height="64" label="Orders" chromeColor="#2259AA"
fontSize="10" icon="#Embed('assets/doc_lines_stright.png')"/>
<s:Button x="241" y="624.5" width="25%" height="64" label="Help" chromeColor="#2259AA"
fontSize="10" icon="#Embed('assets/spechbubble.png')"/>
<s:Button x="360" y="624.5" width="25%" height="64" label="{currencyFormatter.format(cartValue)}" chromeColor="#2259AA"
fontSize="10" icon="#Embed('assets/shop_cart.png')"/>
</s:HGroup>
</s:Group>
RincoTest.mxml
<s:MobileApplication xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
backgroundColor="#000000" firstView="views.RincoTestHome"
>
<fx:Style source="RincoTest.css"/>
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
</fx:Declarations>
<fx:Script>
<![CDATA[
[Bindable]
public var cartValue:int;
]]>
</fx:Script>
<s:titleContent>
<s:Image left="1" top="3" width="173" height="75" backgroundAlpha="1.0" smooth="true"
source="assets/iphone_large.png"/>
</s:titleContent>
<s:navigationContent>
<mx:Spacer width="10" height="82"/>
</s:navigationContent>
</s:MobileApplication>
And this is how I am implementing it
<components:footer x="1.65" y="614.95" width="100%" height="64" cartValue="{cartValue}"/>
I have tried to bind Application.application.cartValue and
MobileApplication.application.cartValue. Neither of them work.
If there is a better way to maintain a cartValue across the entire application please let me know. This is my first attempt with Flex.
Thanks,
Ernie
Use a static variable in the component.
Reference it as ComponentName.staticVar. Usually, everything that needs to know about the global already knows about (e.g. imports) the component file.
Cheers
Another solution is using a singleton pattern: a single instance that everything references through a static accessor.
The effect is about the same. The only advantage to a static reference to an instance over static properties is that the instance can be part of an inheritance and can fulfill an interface.
I've also had some intermittent problems with binding to static values, but that might have been a previous version, PEBCAK, etc.
Cheers