JavaFX start method everytime included tabcontent is called - tabs

How can I start a method every time a tab is called? I have a Main.fxml with a tabpane and two tabs, I've included a separate fxml for each tab (tab1.fxml, tab2.fxml).
Main.fxml
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.*?>
<?import java.lang.*?>
<?import javafx.scene.layout.*?>
<?import javafx.scene.layout.AnchorPane?>
<AnchorPane prefHeight="434.0" prefWidth="428.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="controller.MainController">
<children>
<TabPane prefHeight="434.0" prefWidth="428.0" tabClosingPolicy="UNAVAILABLE" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0">
<tabs>
<Tab fx:id="tab1" text="Tab 1">
<content>
<fx:include source="tab1.fxml" />
</content>
</Tab>
<Tab fx:id="tab2" onSelectionChanged="#addView" text="Tab 2">
<content>
<fx:include source="tab2.fxml" />
</content>
</Tab>
</tabs>
</TabPane>
</children>
</AnchorPane>
MainController.java
public class MainController implements Initializable{
#FXML private Tab tab1;
#FXML private Tab tab2;
#Override
public void initialize(URL arg0, ResourceBundle arg1) {
}
#FXML public void addView(){
}
}
Each FXML has a Label which should show how often the tab(content) was called. So if I click on tab ("tab2") the counter label should show "1" and increment by +1 every time I call this tab again. This should happen by using a method within the tab controllers.
tab1.fxml
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.*?>
<?import java.lang.*?>
<?import javafx.scene.layout.*?>
<?import javafx.scene.layout.AnchorPane?>
<AnchorPane prefHeight="249.0" prefWidth="257.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="controller.tab1Controller">
<children>
<Label fx:id="lbl_1" layoutX="92.0" layoutY="53.0" text="not clicked" />
</children>
</AnchorPane>
tab1Controller.java
public class tab1Controller implements Initializable{
#FXML public Label lbl_1;
private static int counter=0;
#Override
public void initialize(URL arg0, ResourceBundle arg1) {
}
public void addViewCounter(){
lbl_1.setText(""+counter);
counter++;
}
}
Tab2.fxml
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.*?>
<?import java.lang.*?>
<?import javafx.scene.layout.*?>
<?import javafx.scene.layout.AnchorPane?>
<AnchorPane prefHeight="249.0" prefWidth="257.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="controller.tab2Controller">
<children>
<Label fx:id="lbl_2" layoutX="92.0" layoutY="53.0" text="not clicked" />
</children>
</AnchorPane>
tab2Controller.java
public class tab1Controller implements Initializable{
#FXML public Label lbl_2;
private static int counter=0;
#Override
public void initialize(URL arg0, ResourceBundle arg1) {
}
public void addViewCounter(){
lbl_2.setText(""+counter);
counter++;
}
}
I've already tried to solve this problem by using static methods and labels but i get NullPointerExceptions, seems like this doesn't work anymore with java 8.
Also I've tried to get the controller by using a FXMLloader ... this way I also get a NullPointerExceptions.
Isn't there an onCall method for the included fmxl or the anchorpane? Or maybe something that makes the controller initialize again.
Any other solutions or ideas?

Firstly, your counters should not be static. They belong to the controller instances, not the controller class.
You need three things:
A reference to the tabPane in the main controller
A reference to each of the tab controllers in the main controller.
A listener on the tabPane's selected tab, so that you can call a method when the selected tab changes
For the first, just do:
<TabPane fx:id="tabPane" prefHeight="434.0" ... >
in Main.fxml, and
#FXML private TabPane tabPane ;
in MainController.java.
For the second, you can use the "Nested Controller" technique.
You need to add an fx:id attribute to each of the fx:includes, and then just add references for the controllers in MainController.java. The rule is that if your fx:include has fx:id="x", then the controller from the corresponding FXML file can be injected into a variable with name xController. Here I have changed the class names for the controllers to Tab1Controller and Tab2Controller to follow the standard conventions (and avoid confusion).
In Main.fxml, change the fx:includes to include an fx:id:
<fx:include fx:id="tab1Content" source="tab1.fxml" />
<fx:include fx:id="tab2Content" source="tab2.fxml" />
In MainController.java:
#FXML private Tab1Controller tab1ContentController ;
#FXML private Tab2Controller tab2ContentController ;
Now in MainController's initialize() method just set up the listener:
public void initialize() {
tabPane.getSelectionModel().selectedItemProperty()
.addListener((obs, oldTab, newTab) -> {
if (newTab == tab1) {
tab1ContentController.addViewCounter();
} else if (newTab == tab2) {
tab2ContentController.addViewCounter();
}
});
}

Related

Eexpand 2 more Titledpanes at once

On these days i am refactoring java swing code to javafx.
And about some jpanels, i just refactored as JFXPanel and that JFXPanels` root is VBOX. the structure of JFXPanel is VBOX -> BorderPane -> TitledPane -> AnchorPane.
<VBox maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="93.0" prefWidth="295.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1">
<children>
<BorderPane prefHeight="259.0" prefWidth="309.0">
<top>
<TitledPane animated="false" prefHeight="93.0" prefWidth="297.0" style="-fx-background-color: #eeeeee;" text="Compensation Options" textFill="#1b75bc">
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="295.0" prefWidth="267.0">
<children>
<Button fx:id="mResetCountButton" layoutX="25.0" layoutY="5.0" mnemonicParsing="false" text="Reset Counts" textAlignment="CENTER" />
<Button fx:id="plotStatsButton" layoutX="123.0" layoutY="5.0" mnemonicParsing="false" text="Stats Panel" textAlignment="CENTER" />
<Button fx:id="gateStatsButton" layoutX="208.0" layoutY="5.0" mnemonicParsing="false" text="Gate State" textAlignment="CENTER" />
<Button fx:id="mLoadMatrixButton" layoutX="28.0" layoutY="37.0" mnemonicParsing="false" text="Load Matrix" textAlignment="CENTER" />
<Button fx:id="viewCompMatrix" layoutX="119.0" layoutY="37.0" mnemonicParsing="false" text="View Matrix" textAlignment="CENTER" />
<Label fx:id="mJCompMatrixCombo" layoutX="208.0" layoutY="41.0" text="Matrix Name" />
</children>
</AnchorPane>
</content>
</TitledPane>
</top>
</BorderPane>
</children>
</VBox>
And now i want to make JFXPanels as Accordion. When i searched in google i just saw some code which use and when i make Accordion tag, i just can use TitledPane below tag.
Is there any other way to make JFXPanels as Accordion reusing my code?...
And actually using Tag, i just can expand one titledPane at once.
How can i make JavaFX application with Accordion which can expand many titledPanes at once?
I just tried as make titledPanesclicklistener and resizing VBox which is wrapping titledPane and titledpanes size and some panes which in inside of titledpane.
such as
boolean titledPaneClicked = false;
TiteldPane.setOnAction((e)->{
if(titledPaneClicked){
TitledPane.setHeight(0);
Vbox.setHeight(0);
soemotherPanes.setHeight(0);
titledPaneClicked = !titledPaneClicked;
}else{
TitledPane.setHeight(previousSize);
Vbox.setHeight(previousSize);
soemotherPanes.setHeight(previousSize);
titledPaneClicked = !titledPaneClicked;
}
});
And it did not work. Plz help me :)
If your question is about how you can open close 2 TitledPanes at once, you can do so programmatically, for example by using a button :
Main.fxml (to make your code mcve always post the fxml name and imports)
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.Button?>
<?import javafx.scene.control.Label?>
<?import javafx.scene.control.TitledPane?>
<?import javafx.scene.layout.AnchorPane?>
<?import javafx.scene.layout.BorderPane?>
<?import javafx.scene.layout.VBox?>
<VBox minWidth="-Infinity" prefHeight="200.0" prefWidth="200.0" xmlns="http://javafx.com/javafx/10.0.1" xmlns:fx="http://javafx.com/fxml/1"
fx:controller="tests.xml.Controller">
<children>
<BorderPane>
<top>
<TitledPane fx:id="aTitledPane" animated="false" style="-fx-background-color: #eeeeee;" text="Compensation Options" textFill="#1b75bc">
<content>
<AnchorPane>
<children>
<Label text="Top pane expanded" />
</children>
</AnchorPane>
</content>
</TitledPane>
</top>
<center>
<TitledPane fx:id="bTitledPane" animated="false" style="-fx-background-color: #eeeeee;" text="Other Options" textFill="#1b75bc">
<content>
<AnchorPane>
<children>
<Label text="Bottom pane expanded" />
</children>
</AnchorPane>
</content>
</TitledPane>
</center>
<bottom>
<Button fx:id="openCloseButton" onAction="#openClose" text="Close" textAlignment="CENTER" />
</bottom>
</BorderPane>
</children>
</VBox>
And it controller:
import javafx.fxml.FXML;
import javafx.scene.control.Button;
import javafx.scene.control.TitledPane;
public class Controller {
#FXML
private TitledPane aTitledPane, bTitledPane;
#FXML
private Button openCloseButton;
private final static String OPEN = "Open", CLOSE = "Close";
#FXML
void initialize(){
openCloseButton.setText(OPEN);
aTitledPane.setExpanded(false);
bTitledPane.setExpanded(false);
}
#FXML
private void openClose(){
System.out.println(openCloseButton.getText());
if(openCloseButton.getText().equals(OPEN)){
openCloseButton.setText(CLOSE);
aTitledPane.setExpanded(true);
bTitledPane.setExpanded(true);
}else{
openCloseButton.setText(OPEN);
aTitledPane.setExpanded(false);
bTitledPane.setExpanded(false);
}
}
}
Test it using :
import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.stage.Stage;
public class FXMLTest extends Application {
#Override
public void start(Stage primaryStage) throws Exception{
Parent root = FXMLLoader.load(getClass().getResource("xml/Main.fxml"));
primaryStage.setTitle("Hello World");
Scene scene = new Scene(root);
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args) {
launch(null);
}
}
If you want that opening / closing one TitledPane will open / close the other without using a button, remove the button from the fxml, and bind TitledPane.expandedProperty() of the two TitledPanes in the controller:
import javafx.fxml.FXML;
import javafx.scene.control.TitledPane;
public class Controller {
#FXML
private TitledPane aTitledPane, bTitledPane;
#FXML
void initialize(){
aTitledPane.expandedProperty().bindBidirectional(bTitledPane.expandedProperty());
}
}
I solved this problem just using VBox.
I made VBox, titledPane and VBox which contains some Btns, Labels, and so on.
VBox mainBox = new VBox();
TitledPane T1 = new TitledPane();
VBox content1 = new VBox();
T1.setContent(content1);
TitledPane T2 = new TitledPane();
VBox content2 = new VBox();
T2.setContent(content2);
mainBox.getChildren().addAll(T1, T2);
and then in MainVBox, titledPanes are shown like accordion.

Adding java swing combobox to javafx application

I am trying to create a javafx application witch contanis just a tab pane and javafx combo box , this is my fxml witch i created by scene builder :
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.ComboBox?>
<?import javafx.scene.control.Tab?>
<?import javafx.scene.control.TabPane?>
<?import javafx.scene.layout.AnchorPane?>
<AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="288.0" xmlns="http://javafx.com/javafx/8.0.111" xmlns:fx="http://javafx.com/fxml/1">
<children>
<TabPane layoutX="-2.0" prefHeight="400.0" prefWidth="288.0" tabClosingPolicy="UNAVAILABLE">
<tabs>
<Tab text="tab1">
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="180.0" prefWidth="200.0">
<children>
<ComboBox layoutX="32.0" layoutY="39.0" prefHeight="26.0" prefWidth="86.0" />
</children>
</AnchorPane>
</content>
</Tab>
</tabs>
</TabPane>
</children>
</AnchorPane>
and this is my simple Main just for call fxml
import javafx.application.Application;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.event.EventHandler;
import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader;
import javafx.scene.Scene;
import javafx.scene.control.TableColumn;
import javafx.scene.control.TableView;
import javafx.scene.control.cell.PropertyValueFactory;
import javafx.scene.input.MouseEvent;
import javafx.stage.Stage;
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
/**
*
* #author asus
*/
public class Main extends Application{
#Override
public void start(Stage primaryStage) throws Exception {
Scene scene= new Scene(FXMLLoader.load(getClass().getResource("/javaapplication3/test.fxml")));
primaryStage.setScene(scene);
primaryStage.setX(0);
primaryStage.show();
}
public static void main(String[] args) {
launch();
}
}
I am looking for a way to use swing combobox wich integerated with my fxml file and my application How can I do it , is there any way to use swing component in scene builder of fxml?

Json Root Name not coming in Camel Swagger Rest Service

I am trying to create rest service using apache camel swagger component.
Now i have this camel context as:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:camel="http://camel.apache.org/schema/spring"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd">
<!-- a bean for user services -->
<bean id="personService" class="www.tempuri.person.PersonService"/>
<camelContext id="myCamel" xmlns="http://camel.apache.org/schema/spring">
<restConfiguration component="servlet" bindingMode="auto" contextPath="myService/rest" port="8080">
<dataFormatProperty key="prettyPrint" value="true"/>
</restConfiguration>
<!-- defines the rest services using the context-path /Equipment -->
<rest path="/getPerson/persons" consumes="application/json,application/xml" produces="application/json,application/xml">
<description>Person rest service</description>
<post uri="/search" type="www.tempuri.person.model.GetPerson"
outType="www.tempuri.person.model.GetPerson">
<description>Get Person(s)</description>
<param name="body" type="body" description="Get Person(s)" required="true"/>
<responseMessage code="400" message="Bad Request" />
<responseMessage code="200" message="Person Data" />
<responseMessage code="401" message="Unauthorized" />
<to uri="bean:personService?method=getPersons"/>
</post>
</rest>
</camelContext>
</beans>
And below is my model class GetPerson:
package www.tempuri.person.model;
import javax.xml.bind.annotation.XmlRootElement;
import com.fasterxml.jackson.annotation.JsonRootName;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
#ApiModel(description = "Represents Persons")
#XmlRootElement(name="getPerson")
#JsonRootName(value = "getPerson")
public class GetPerson {
#ApiModelProperty(value = "Application Area of GetPerson", required = true)
private ApplicationArea applicationArea;
#ApiModelProperty(value = "Data Area of GetPerson", required = true)
private DataArea dataArea;
/**
* #return the dataArea
*/
public DataArea getDataArea() {
return dataArea;
}
/**
* #param dataArea the dataArea to set
*/
public void setDataArea(DataArea dataArea) {
this.dataArea = dataArea;
}
public ApplicationArea getApplicationArea() {
return applicationArea;
}
public void setApplicationArea(ApplicationArea applicationArea) {
this.applicationArea = applicationArea;
}
}
Now in case of application xml it is working good and the request structure has a root element as getPerson, but in case of JSON Request it doesn't show the root element getPerson. I know that there is something called WRAP_ROOT_VALUE which can be used to enable the root name in case of json. But the problem is i don't know how to do it using camel-config.xml.
How can i set the WRAP_ROOT_VALUE through my camel-config.xml or is there some other way. Thanks in advance..

how to display android mapfragment view rounded shape

i have to show map view in rounded shape , is it posible to show android map view with rounded shape.
I have tried to applying fragment layout gadient but after map loading is showing rectange view.
any guidence for to make android rounded mapview
Yes, it possible. Cover the MapFragment with another layout, and set for this layout a 9-patch background, that will cover it the way you want, take a look at this question I asked on the same topic not long ago:
Is there a way to implement rounded corners to a Mapfragment?
You can use shapes in layer-list
here is the shape_circle.xml
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<item android:drawable="#drawable/shape_circle_rect"/>
<item android:drawable="#drawable/shape_circle_oval"/>
</layer-list>
shape_circle_rect.xml
<?xml version="1.0" encoding="utf-8"?>
<shape
xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid android:color="#android:color/transparent"/>
<stroke android:width="50dp" android:color="#ffffff"/>
<padding
android:left="-50dp"
android:top="-50dp"
android:right="-50dp"
android:bottom="-50dp"/>
</shape>
shape_circle_oval.xml
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="oval" >
<stroke android:color="#ffffff" android:width="100dp"/>
<solid android:color="#android:color/transparent"/>
</shape>
and Custom Map Fragment
public class MapFragment extends SupportMapFragment{
//...
//Some methods, set up map and etc.
//...
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup viewGroup, Bundle bundle) {
View mapView = super.onCreateView(inflater, viewGroup, bundle);
RelativeLayout view = new RelativeLayout(getActivity());
view.addView(mapView, new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.MATCH_PARENT, RelativeLayout.LayoutParams.MATCH_PARENT));
FrameLayout frameLayout=new FrameLayout(getActivity());
frameLayout.setLayoutParams(new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, FrameLayout.LayoutParams.MATCH_PARENT));
frameLayout.setBackgroundResource(R.drawable.shape_circle);
view.addView(frameLayout);
return view;
}
//...
//...
}

Adding export option to Office 2010 backstage view

I cannot extend Office 2010 UI even when I use the code from MSDN. This is the code I think should work:
<?xml version="1.0" encoding="UTF-8"?>
<customUI xmlns="http://schemas.microsoft.com/office/2009/07/customui" onLoad="Ribbon_Load">
<backstage>
<tab idMso="TabShare">
<firstColumn>
<taskFormGroup idMso="GroupShare">
<category idMso="FileTypes">
<task id="tskExportXmlCms" label="Exportovat jako XML">
<group id="grpExportXmlCms" label="Exportovat jako XML">
<topItems>
<button id="btnExportXmlCms" label="Exportovat jako XML" onAction="OnExportXmlCms" />
</topItems>
</group>
</task>
</category>
</taskFormGroup>
</firstColumn>
</tab>
</backstage>
</customUI>
public void OnExportXmlCms(IRibbonControl control) { }
When I add Ribbon (Visual Designer) I can see added items. When I use Ribbin (XML) I'm not able to see anything in the backstage. What is wrong?
There was missing this method:
public partial class ThisAddIn {
protected override Office.IRibbonExtensibility CreateRibbonExtensibilityObject() {
return new Ribbon();
}
}