eclipse capitolo7: Transitions for Windows, Dialogs and Perspectives
1. 7
Transitions for Windows, Dialogs and
Perspectives (ch07-rev.01-15072018 firmani
nelson)
Le classi che forniscono l’animazione in JavaFX si trovano nel pacchetto javafx.animation.
Un’animazione in javaFX si realizza con una variazione delle proprietà associate a un nodo, come dimensioni,
posizione e colore.
Sono controllate da una "timeline" cioè un’arco di tempo che fornisce la capacità di aggiornare i valori delle
proprietà lungo la progressione del tempo.
Le timeline usano i keyframes (fotogrammi chiave) per definire le variabili i cui valori devono essere fissati a
istanti specifici dell’animazione. Poi il sistema attraverso le interpolazioni che occorrono tra un key frame e
l’altro può eseguire automaticamente l’animazione.
E' possibile animare qualsiasi nodo per produrre effetti di dissolvenza, traslazione, rotazione, etc.
Per farlo, è necessario istanziare la rispettiva classe di transizione (animazione) che deve essere applicata al
nodo, impostare le proprietà della transizione e infine, eseguire la transizione usando il metodo play () della
classe Animation.
Esistono inoltre metodi per interrompere, sospendere, riprendere, invertire o ripetere movimenti quando
richiesto.
Figura 7.1. UML javafx.animation.Animation
FadeTransition
graduale scomparsa di un nodo modificando la proprietà di opacità da un valore iniziale a un valore finale
con una durata specificata dalla proprietà duration
ParallelTransition
Esegue più transizioni simultaneamente.
PathTransition
sposta un nodo lungo un percorso geometrico aggiornando le proprietà translateX e translateY della
proprietà del nodo con durata specificata dalla proprietà duration
149
2. SequentialTransition
Esegue più transizioni uno dopo l’altra.
FillTransition
modifica il colore di riempimento di una forma da un colore iniziale a un colore finale secondo una durata
specificata
PauseTransition
attende la scadenza del valore della proprietà duration e quindi esegue il gestore eventi assegnato alla
sua proprietà onFinished
RotateTransition
ruota un nodo attorno al suo centro variando la proprietà di rotazione del suo nodo da un valore iniziale a
un valore finale (entrambi in gradi) con durata specificata dalla proprietà duration.
ScaleTransition
cambia la proprietà scaleX , scaleY e Scalez degli oggetti di un nodo da un valore iniziale a un valore finale
secondo una durata specificata.
TranslateTransition
modifica le proprietà translateX , translateY e translateZ di una proprietà del nodo da un valore iniziale ad
un valore finale per la durata specificata dalla proprietà duration
I valori delle proprietà coinvolte tra i keyframes vengono definite automaticamente mediante interpolazione.
E' possibile utilizzare varie implementazioni integrate della classe Interpolator oppure implementare il proprio
Interpolatore per ottenere un comportamento di interpolazione personalizzato.
Figura 7.2. UML javafx.animation.Interpolator
JavaFX fornisce diversi interpolatori utilizzabili per creare effetti diversi nell’animazione.
150
3. Per impostazione predefinita, JavaFX utilizza l’interpolazione lineare per calcolare i valori delle proprietà.
Interpolator.LINEAR
è l’interpolatore di default. Il cambiamento nel valore della variabile associata è proporzionale allo scorrere
del tempo;
interpolator.DISCRETE
questo interpolatore permette alla variabile di conservare il suo valore iniziale fino alla fine del keyframe,
e a quel punto viene assegnato il valore;
Interpolator.EASIN
ha le stesse proprietà dell’Interpolator.LINEAR ma il valore cambia più lentamente all’avvio del keyframe;
Interpolator.EASEOUT
ha le stesse proprietà dell’Interpolator.LINEAR ma il valore cambia più lentamente alla fine del keyframe;
Interpolaor.EASEBOTH
ha le stesse proprietà dell’Interpolator.LINEAR ma il valore cambia più lentamente all’inizio e alla fine del
keyframe;
Interpolator.SPLINE
il modo in cui il valore della variabile cambia dipende da una curva spline associata con l’Interpolator.
151
4. Windows
Nelle applicazioni Eclipse RCP con JavaFX la transizione da finestra aperta a finestra
chiusa e viceversa, l’animazione di finestre di dialogo e la transizione di prospettive
(perspective) avvengono attraverso l’implementazione di servizi OSGi.
7.1. Windows
La transizione da finestra aperta a finestra chiusa e viceversa avviene attraverso l’implementazione di un
servizio OSGi
la cui interfaccia esposta dal bundle
org.eclipse.fx.ui.workbench.renderers.base.services è
org.eclipse.fx.ui.workbench.renderers.base.services.WindowTransitionService<Stage>
I servizi OSGi possono essere definiti in modo dichiarativi in un file xml.
L’IDE eclipse attraverso una procedura guidata permette la creazione di un file xml con le informazioni
necessarie per la definizione del componente (servizio OSGi).
Elementi essenziali del file sono il nome della classe dell’istanza del componente e l’interfaccia del servizio
fornito.
La procedura guidata inoltre aggiunge il riferimento di questo file al file MANIFEST.MF
OSGI-INF/services/window-transition.xml.
<?xml version="1.0" encoding="UTF-8"?>
<scr:component xmlns:scr="http://www.osgi.org/xmlns/scr/
v1.1.0" enabled="true" name="it.nelson.xbrl.client.app.WindowTransition">
<implementation class="it.nelson.xbrl.client.app.WindowTransition"/>
<service>
<provide interface="org.eclipse.fx.ui.workbench.renderers.base.services.WindowTransitionService"/
>
</service>
</scr:component>
Nel MANIFEST.MF alla voce Service-Component c'è il riferimento ai file che descrivono i componenti, questi
file in genere si creano in una cartella di nome OSGI-INF.
META-INF/MANIFEST.MF.
Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: My Sample App
Bundle-SymbolicName: it.nelson.xbrl.client.app;singleton:=true
Bundle-Version: 1.0.1.qualifier
Require-Bundle: org.eclipse.fx.ui.workbench.fx,
...
Bundle-RequiredExecutionEnvironment: JavaSE-1.8
Import-Package: javax.inject;version="1.0.0",
...
Bundle-ActivationPolicy: lazy
Service-Component: OSGI-INF/services/window-transition.xml
Creazione del componente (servizio) OSGi attraverso la procedura guidata disponibile dall’ide eclipse.
152
5. Windows
Figura 7.3. Wizard per la creazione del servizio window transition
Creazione della classe WindowTransition.
Figura 7.4. Creazione della classe di implementazione del servizio
Riferimento alla classe WindowTransition.
153
6. Windows
Figura 7.5. Riferimento alla classe del servizio
Figura 7.6. Descrizione xml del servizio
La descrizione del componente attraverso il file xml contiene tutte le informazioni del servizio, nome, classe
e interfaccia del servizio
154
7. Windows
Figura 7.7. Sezione Services per selezionare l’interfaccia del servizio da implementare
org.eclipse.fx.ui.workbench.renderers.base.services.WindowTransitionService come interfaccia del
servizio
Figura 7.8. Selezionata l’interfaccia WindowsTransitionService
155
8. Windows
Figura 7.9. file window-transition.xml
Implementazione della classe WindowTransition:
La transizione (animazione) avviene attraverso l’implementazione del metodo
animate(@NonNull C window, @NonNull Runnable finished)
del tipo
AnimationDelegate<Node>
definito come interfaccia annidata dell’interfaccia
WindowTransitionService<Node>
Figura 7.10. UML WindowTransition
156
9. Windows
Figura 7.11. La classe WindowTransition
Figura 7.12. La classe StageFadeTransition
157
11. Windows
Figura 7.15. Verifica fade-transition apertura window
Possibilità di abilitare o disabilitare il servizio dal file descrittore del servizio.
Figura 7.16. Abilitare/Disabilitare il servizio window transition
159
12. Windows
Figura 7.17. Servizio window transition disabilitato
Dunque in sintesi il file window-transition.xml definisce un componente di nome
it.nelson.xbrl.client.app.WindowTransition
che fornisce un servizio al OSGi-service-registry per l’interfaccia
org.eclipse.fx.ui.workbench.renderers.base.services.WindowTransitionService.
Servizio implementato dalla classe it.nelson.xbrl.client.app.WindowTransition (non è necessario che il nome
della classe e il nome del componente coincidono) il cui sorgente è:
/it.nelson.xbrl.client.app/src/it/nelson/xbrl/client/app/WindowTransition.java.
package it.nelson.xbrl.client.app;
import org.eclipse.e4.ui.model.application.ui.basic.MWindow;
import org.eclipse.fx.ui.workbench.renderers.base.services.WindowTransitionService;
import org.osgi.service.component.annotations.Component;
import javafx.stage.Stage;
import javafx.util.Duration;
@SuppressWarnings("restriction")
@Component
public class WindowTransition implements WindowTransitionService<Stage> {
@Override
public AnimationDelegate<Stage> getShowDelegate(
MWindow window) {
return new AnimationDelegate<Stage>() {
@Override
public void animate(Stage window, Runnable finished) {
window.setOpacity(0);
window.show();
StageFadeTransition fade = new StageFadeTransition(window, 0, 1, Duration.millis(3000)); //fade
transition di 3 secondi
fade.setOnFinished( e -> finished.run());
fade.play();
}
};
}
@Override
public AnimationDelegate<Stage> getHideDelegate(
MWindow window) {
return null;
}
}
160
13. Dialogs
/it.nelson.xbrl.client.app/src/it/nelson/xbrl/client/app/StageFadeTransition.java.
package it.nelson.xbrl.client.app;
import javafx.animation.Transition;
import javafx.stage.Stage;
import javafx.util.Duration;
public class StageFadeTransition extends Transition {
private final Stage stage;
private final double start;
private final double delta;
public StageFadeTransition(Stage stage, double start, double end, Duration duration) {
this.stage = stage;
this.start = start;
this.delta = end - start;
setCycleDuration(duration);
}
@Override
protected void interpolate(double frac) {
double v = start + frac * delta;
final double newOpacity = Math.max(0.0,
Math.min(v, 1.0));
stage.setOpacity(newOpacity);
}
}
7.2. Dialogs
Il sistema di dialogo è costruito attorno alla classe base org.eclipse.fx.ui.controls.dialog.Dialog con le classi
derivate:
1. TitleAreaDialog (finestra di dialogo con un’area riservata in alto per visualizzare le informazioni)
2. MessageDialog (QUESTION, INFORMATION, WARNING, ERROR, CONFIRM, QUESTION_CANCEL)
Le applicazioni eclipse RCP (E4) con javafx possono utilizzare le finestre di dialogo attraverso un nuovo servizio
denominato
org.eclipse.fx.ui.services.dialog.LightWeightDialogService
così l’apertura di una finestra di dialogo può essere eseguita con:
@Execute
public void openDialog(LightWeightDialogService service) {
MyDialog d = new MyDialog();
service.openDialog(d, ModalityScope.WINDOW);
}
161
14. Dialogs
Figura 7.18. UML LightWeightDialogService
Figura 7.19. UML Dialog
La classe TestDialogHandler.
package it.nelson.xbrl.client.app.handlers;
import org.eclipse.e4.core.di.annotations.Execute;
import org.eclipse.fx.ui.services.dialog.LightWeightDialogService;
import org.eclipse.fx.ui.services.dialog.LightWeightDialogService.ModalityScope;
public class TestDialogHandler {
@Execute
public void execute(LightWeightDialogService dialogService) {
MyDialog myDialog = new MyDialog("frame title", "title", "message");
dialogService.openDialog(myDialog, ModalityScope.WINDOW);
}
}
La classe myDialog.
package it.nelson.xbrl.client.app.handlers;
import org.eclipse.fx.ui.controls.dialog.TitleAreaDialog;
import javafx.scene.control.Button;
162
15. Dialogs
import javafx.scene.control.Hyperlink;
import javafx.scene.control.Label;
import javafx.scene.layout.BorderPane;
@SuppressWarnings("restriction")
public class MyDialog extends TitleAreaDialog {
public MyDialog(String frameTitle, String title, String message) {
super(frameTitle, title, message);
// nodo che riempie la client area
Label lbtop = new Label("Client area border layout (top)");
Button btnr = new Button("Right");
Button btnl = new Button("Left");
Button btnc = new Button("Center");
Hyperlink link = new Hyperlink("Bottom");
BorderPane clientArea = new BorderPane(btnc, lbtop, btnr, link, btnl);
//
setClientArea(clientArea);
addDefaultButtons();
// setMaxHeight(500);
setPrefHeight(400);
setPrefWidth(500);
setId("test-dialog"); // id selector template css
}
}
Css dialog.
/* Css dialog */
.efx-dialog-title-image {
-fx-image: url(icons/64/applications-system.png);
}
#open-project-dialog .efx-dialog-title-image {
-fx-image: url(icons/64/prj_obj.png);
}
#open-project-dialog .efx-dialog-messageArea-area {
-fx-background-color: rgb(192.0,192.0,192.0) ;
}
#test-dialog .efx-dialog-title-image {
-fx-image: url(icons/64/application-x-java.png);
}
#test-dialog .efx-dialog-graphic-container {
-fx-background-color: blue ;
}
#test-dialog .efx-dialog-messageArea-area {
-fx-background-color: red ;
}
#test-dialog .efx-dialog-title {
/* -fx-background-color: beige ; */
-fx-font-size: 16pt;
163
16. Dialogs
}
#test-dialog .efx-dialog-title-message {
-fx-font-size: 14pt;
}
#test-dialog .efx-dialog-title-font-icon {
}
Figura 7.20. Finestra MyDialog di tipo TitleAreaDialog
Creazione di una finestra di dialogo di tipo TitleAreaDialog con una client area costituita da una lista di elementi.
Figura 7.21. Menu, comando e gestore dell’apertura della finestra di esempio
164
18. Dialogs
Figura 7.24. Finestra di dialogo in esecuzione
Mentre la classe TitleAreaDialog consente di creare facilmente una finestra di dialogo di tipo pop-up con uno
spazio riservato per fornire feedback all’utente e creare un proprio layout,
la classe MessageDialog consente all’utente di essere avvisato di qualcosa o confermare una domanda tipo
yes/no/cancel.
Tutte le finestre di dialogo (TitleAreaDialog e MessageDialog) create sono modali cioè blocca il thread corrente
fino a quando l’interazione con l’utente non è stata completata.
Esempio di finestra di conferma.
package it.nelson.xbrl.client.app.lifecycle;
import org.eclipse.e4.ui.model.application.ui.basic.MWindow;
import org.eclipse.fx.ui.dialogs.MessageDialog;
import org.eclipse.fx.ui.dialogs.MessageDialog.ConfirmResult;
import org.eclipse.fx.ui.workbench.renderers.base.widget.WWindow;
import org.eclipse.fx.ui.workbench.services.lifecycle.annotation.PreClose;
import org.eclipse.fx.ui.workbench.services.lifecycle.annotation.PreShow;
import javafx.stage.Stage;
public class LifeCycle {
@PreShow
public void execute() {
System.err.println("PreShow");
}
@PreClose
public boolean ph(MWindow win) {
System.err.println("PreClose");
166
19. Dialogs
if (MessageDialog.openConfirmDialog((Stage) ((WWindow) win.getWidget()).getWidget(), "Messaggio
di conferma",
"Conferma chiusura scheda?") == ConfirmResult.OK)
return true;
else
return false;
}
}
Figura 7.25. Esempio di finestra di conferma
Esempio di finestra di informazione.
...
@FXML
void actSave(ActionEvent event) {
bookService.addBook(DATASOURCE.get(idListView.getSelectionModel().getSelectedIndex()));
MessageDialog.openInformationDialog(stage, "Conferma",
"Salvato libro con id= " +
DATASOURCE.get(idListView.getSelectionModel().getSelectedIndex()).getId());
}
...
167
20. Dialogs
Figura 7.26. Esempio di finestra di informazione
Esempio di finestra di errore.
...
try {
bookService.init();
} catch (Throwable e) {
System.err.println("Impossibile stabilire connessione con il DB");
MessageDialog.openErrorDialog(stage, "ERRORE DI CONNESSIONE",
"Non posso creare EntityManagerFactory: " + e.getMessage());
throw new ExceptionInInitializerError(e);
}
...
168
21. Dialogs
Figura 7.27. Esempio di finestra di errore
Mentre il servizio di dialogo consente di aprire una finestra di dialogo e controllare la sua modalità, c'è un
secondo servizio che è in grado di controllare come viene mostrata / nascosta una finestra di dialogo.
Di default la finestra di dialogo è semplicemente mostrata e nascosta ma si possono aggiungere anche delle
animazioni come mostrato di seguito
La finestra di dialogo può essere aperta in modo animato attraverso l’implementazione di un servizio OSGi la
cui interfaccia esposta dal bundle
org.eclipse.fx.ui.workbench.renderers.fx.services
è
org.eclipse.fx.ui.workbench.renderers.fx.services.LightweightDialogTransitionService
Il package package org.eclipse.fx.ui.workbench.renderers.fx.services fornisce delle classi di transizioni delle
finestre di dialogo
con l’implementazioni di transizioni (animazioni) predefinite:
1. FadeDialogTransitionService: classe astratta da ereditare per implementare una transizione della finestra
di dialogo per dissolvenza, la classe derivata può riscrivere i metodi ereditati per variare le proprietà
dell’animazione:
• protected void configureFadeIn(FadeTransition transition)
• protected void configureFadeOut(FadeTransition transition)
2. FlyInTransitionService: classe concreta da ereditare per implementare transizione per variazione della
posizione verticale (apertura dall’alto verso il basso chiusura dal basso verso l’alto)
169
22. Dialogs
Figura 7.28. UML DialogTransitionService
Esempio di implementazione del servizio di trasparenza finestre di dialogo
package it.nelson.xbrl.client.app;
import org.eclipse.fx.ui.workbench.renderers.fx.services.FadeDialogTranstionService;
import org.eclipse.fx.ui.workbench.renderers.fx.services.LightweightDialogTransitionService;
import org.osgi.service.component.annotations.Component;
import javafx.animation.FadeTransition;
import javafx.animation.Interpolator;
import javafx.util.Duration;
@Component(service = LightweightDialogTransitionService.class)
public class DialogTransition extends FadeDialogTranstionService {
@Override
protected void configureFadeIn(FadeTransition transition) {
super.configureFadeIn(transition);
transition.setInterpolator(Interpolator.EASE_IN);
transition.setDuration(Duration.millis(600));
}
@Override
protected void configureFadeOut(FadeTransition transition) {
super.configureFadeOut(transition);
transition.setInterpolator(Interpolator.EASE_OUT);
transition.setDuration(Duration.millis(600));
}
}
170
23. Dialogs
Figura 7.29. Definizione servizio transizione della finestra di dialogo
Figura 7.30. Nome e riferimento della classe del servizio
171
24. Dialogs
Figura 7.31. Ricerca dell’interfaccia che fornisce il servizio
Figura 7.32. Interfaccia che fornisce il servizio
172
25. Dialogs
Figura 7.33. Classe che implementa il servizio di transizione per dissolvenza
FadeDialogTranstionService è la classe che implementa la transizione per dissolvenza, la classe derivata può
riscrivere i metodi ereditati:
• protected void configureFadeIn(FadeTransition transition)
• protected void configureFadeOut(FadeTransition transition)
Figura 7.34. Riscrittura metodi ereditati
173
26. Dialogs
Figura 7.35. Fade transition della finestra di dialogo in esecuzione
Di seguito l’altra animazione predefinita della finestra di dialogo implementata attraverso la classe
FlyInTransitionService
package it.nelson.xbrl.client.app;
import org.eclipse.fx.ui.workbench.renderers.fx.services.FlyInTransitionService;
import org.eclipse.fx.ui.workbench.renderers.fx.services.LightweightDialogTransitionService;
import org.osgi.service.component.annotations.Component;
@Component(property = { "service.ranking:Integer=-1" })
public class FlyinTransitionServiceImpl extends FlyInTransitionService implements
LightweightDialogTransitionService {
}
174
27. Dialogs
Figura 7.36. Nome e riferimento della classe del servizio
Figura 7.37. La classe che implementa il servizio
175
29. Dialogs
Figura 7.40. Finestra di dialogo con animazione predefinita dalla classe FlyInTransitionService
Implementazione di una animazione non predefinita.
Figura 7.41. La classe che implementa il servizio
Figura 7.42. Metodi da implementare segnati dall’interfaccia
177
31. Dialogs
Figura 7.45. Nuovo riferimento di classe nel servizio di transizione della finestra di dialogo
Figura 7.46. Servizio implementato dalla classe MyAnimTransitionServiceImpl
Utilizzando le api di javaFX: fadeTransition e rotateTransition
MyAnimTransitionServiceImpl.java.
package it.nelson.xbrl.client.app;
import org.eclipse.e4.ui.model.application.ui.MUIElement;
import org.eclipse.fx.ui.workbench.renderers.fx.services.LightweightDialogTransitionService;
import org.osgi.service.component.annotations.Component;
import javafx.animation.FadeTransition;
import javafx.animation.Interpolator;
import javafx.animation.ParallelTransition;
import javafx.animation.RotateTransition;
import javafx.animation.TranslateTransition;
import javafx.scene.Node;
import javafx.scene.layout.Pane;
import javafx.util.Duration;
@Component(property = { "service.ranking:Integer=-1" })
public class MyAnimTransitionServiceImpl implements LightweightDialogTransitionService {
private boolean fadeGrayArea;
@Override
179
32. Dialogs
public void showDialog(MUIElement container, Pane containerNode, Pane dialogOverlayContainer, Node
grayArea,
Node dialog, Runnable finished) {
FadeTransition fd = new FadeTransition(Duration.millis(4000), dialogOverlayContainer);
fd.setFromValue(0.0);
fd.setToValue(1.0);
TranslateTransition t = new TranslateTransition(Duration.millis(4000), dialog);
t.setFromY(-1 * (dialog.getLayoutY() + dialog.prefHeight(-1)));
t.setFromX(-1 * (dialog.getLayoutX() + dialog.prefWidth(-1)));
t.setToX(0);
t.setToY(0);
t.setInterpolator(Interpolator.EASE_OUT);
if (finished != null) {
t.setOnFinished(e -> {
finished.run();
});
}
ParallelTransition p = new ParallelTransition(t);
if (this.fadeGrayArea) {
p.getChildren().add(fd);
}
p.play();
}
@Override
public void hideDialog(MUIElement container, Pane containerNode, Pane dialogOverlayContainer, Node
grayArea,
Node dialog, Runnable finished) {
RotateTransition r = new RotateTransition(Duration.millis(2000), dialog);
r.setByAngle(180f);
r.setCycleCount(4);
r.setAutoReverse(true);
if (finished != null) {
r.setOnFinished(e -> {
finished.run();
});
}
r.play();
}
}
otteniamo una animazione di tipo rotazione e dissolvenza
180
33. Dialogs
Figura 7.47. Animazione in esecuzione
Utilizzando le api di javaFX: pathTransition e CubicCurveTo otteniamo una animazione più complessa
@Override
public void hideDialog(MUIElement container, Pane containerNode, Pane dialogOverlayContainer, Node
grayArea,
Node dialog, Runnable finished) {
Path path = new Path();
path.getElements().add(new MoveTo(-30, -30));
path.getElements().add(new CubicCurveTo(400, 0, 400, 100, 200, 100));
path.getElements().add(new CubicCurveTo(0, 100, 0, 240, 400, 240));
PathTransition pathTransition = new PathTransition();
pathTransition.setDuration(Duration.millis(3000));
pathTransition.setPath(path);
pathTransition.setNode(dialog);
pathTransition.setOrientation(PathTransition.OrientationType.ORTHOGONAL_TO_TANGENT);
pathTransition.setCycleCount(2);
pathTransition.setAutoReverse(true);
if (finished != null) {
pathTransition.setOnFinished(e -> {
finished.run();
});
}
pathTransition.play();
}
181
34. Perspective
Figura 7.48. Animazione in esecuzione
7.3. Perspective
La transizione delle prospettive (perspective) avviene attraverso l’implementazione di un servizio OSGi
la cui interfaccia esposta dal bundle
org.eclipse.fx.ui.workbench.renderers.base.services
è
org.eclipse.fx.ui.workbench.renderers.base.services.PerspectiveTransitionService<BorderPane,Node>
Il package org.eclipse.fx.ui.animation.pagetransition.animation fornisce delle classi di transizioni con
l’implementazioni di transizioni (animazioni) predefinite
Figura 7.49. UML org.eclipse.fx.ui.animation.pagetransition
Quindi per realizzare ad esempio una animazione di una prospettiva che si apre con effetto zoom occorre
definire il servizio OSGi descritto nel file perspective-animation.xml
perspective-animation.xml.
<?xml version="1.0" encoding="UTF-8"?>
<scr:component xmlns:scr="http://www.osgi.org/xmlns/scr/v1.1.0" enabled="true"
name="it.nelson.xbrl.client.app.PerspectiveAnimation">
<implementation class="it.nelson.xbrl.client.app.PerspectiveAnimation"/>
<service>
<provide interface="org.eclipse.fx.ui.workbench.renderers.base.services.PerspectiveTransitionService"/
>
</service>
182
35. Perspective
</scr:component>
e la classe it.nelson.xbrl.client.app.PerspectiveAnimation che implementa il servizio:
PerspectiveAnimation.java.
import org.eclipse.e4.ui.model.application.ui.advanced.MPerspective;
import org.eclipse.fx.ui.animation.pagetransition.animation.ZoomSlideAnimation;
import org.eclipse.fx.ui.workbench.renderers.base.services.PerspectiveTransitionService;
import org.osgi.service.component.annotations.Component;
import javafx.scene.Node;
import javafx.scene.layout.BorderPane;
@SuppressWarnings("restriction")
@Component
public class PerspectiveAnimation implements PerspectiveTransitionService<BorderPane, Node> {
@Override
public AnimationDelegate<BorderPane, Node> getDelegate(MPerspective fromPerspective, MPerspective
toPerspective) {
return new AnimationDelegate<BorderPane, Node>() {
@Override
public void animate(BorderPane container, Node control, Runnable finished) {
ZoomSlideAnimation animation = new ZoomSlideAnimation();
animation.animate(container, control, finished);
}
};
}
}
In figura un esempio di implementazione per la transizione di perspective mediante l’animazione predefinita
PageChangeAnimation.
Figura 7.50. Animazione transizione prospettive
Definizione del servizio OSGi mediante il wizard component definition in plug-in development di eclipse
183
39. Perspective
Figura 7.57. Codice dopo importazione package
Figura 7.58. Verifica mediante esecuzione
Realizzazione di una animazione di una prospettiva che si apre con effetto non predefinito ma costruito
attraverso una classe che estende la superclasse CenterSwitchAnimation e l’implementazione dei metodi
ereditati attraverso le api javaFX
187
41. Perspective
Figura 7.61. Descrizione del servizio in xml
Figura 7.62. Classe delegata che implementa l’interfaccia del servizio
Costruzione della classe MyAnimRotate che estende la superclasse CenterSwitchAnimation
189
42. Perspective
Figura 7.63. Creazione della classe MyAnimRotate
Figura 7.64. Sorgente della classe MyAnimRotate
Implementazione dei metodi ereditati dalla superclasse CenterSwitchAnimation mediante le classi javaFX
RotateTransition e FadeTransition
190
43. Perspective
Figura 7.65. Implementazione dei metodi ereditati dalla superclasse CenterSwitchAnimation
Figura 7.66. Animazione cambio prospettiva in esecuzione
Animazione più complessa mediante l’implementazione dei metodi ereditati dalla superclasse
CenterSwitchAnimation con le classi javaFX PathTransition e ScaleTransition
191