View Javadoc
1   /*
2    * *************************************************************************************************************************************************************
3    *
4    * SteelBlue: DCI User Interfaces
5    * http://tidalwave.it/projects/steelblue
6    *
7    * Copyright (C) 2015 - 2025 by Tidalwave s.a.s. (http://tidalwave.it)
8    *
9    * *************************************************************************************************************************************************************
10   *
11   * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License.
12   * You may obtain a copy of the License at
13   *
14   *     http://www.apache.org/licenses/LICENSE-2.0
15   *
16   * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
17   * CONDITIONS OF ANY KIND, either express or implied.  See the License for the specific language governing permissions and limitations under the License.
18   *
19   * *************************************************************************************************************************************************************
20   *
21   * git clone https://bitbucket.org/tidalwave/steelblue-src
22   * git clone https://github.com/tidalwave-it/steelblue-src
23   *
24   * *************************************************************************************************************************************************************
25   */
26  package it.tidalwave.ui.javafx;
27  
28  import jakarta.annotation.Nonnull;
29  import java.util.ArrayList;
30  import java.util.List;
31  import org.springframework.context.ConfigurableApplicationContext;
32  import org.springframework.context.annotation.AnnotationConfigApplicationContext;
33  import org.springframework.context.annotation.Bean;
34  import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
35  import it.tidalwave.ui.javafx.spi.AbstractJavaFXSpringApplication;
36  import org.slf4j.Logger;
37  import org.slf4j.LoggerFactory;
38  import it.tidalwave.util.PreferencesHandler;
39  import it.tidalwave.ui.core.annotation.EnableMessageBus;
40  import it.tidalwave.messagebus.MessageBus;
41  import it.tidalwave.messagebus.spi.SimpleMessageBus;
42  
43  /***************************************************************************************************************************************************************
44   *
45   * A base class for JavaFX applications with use Spring annotation scanning.
46   *
47   * @author  Fabrizio Giudici
48   * @since   1.1-ALPHA-4
49   *
50   **************************************************************************************************************************************************************/
51  public class JavaFXSpringAnnotationApplication extends AbstractJavaFXSpringApplication
52    {
53      static class Beans
54        {
55          @Bean
56          public ThreadPoolTaskExecutor javafxBinderExecutor()
57            {
58              return JavaFXSafeProxyCreator.getExecutor();
59            }
60  
61          @Bean
62          public StackPaneSelector stackPaneSelector()
63            {
64              return new StackPaneSelector();
65            }
66  
67          @Bean
68          public PreferencesHandler preferencesHandler()
69            {
70              return PreferencesHandler.getInstance();
71            }
72  
73          @Bean
74          public JavaFXToolBarControl toolBarControl()
75            {
76              return JavaFXSafeProxyCreator.getToolBarControl();
77            }
78  
79          @Bean
80          public JavaFXMenuBarControl menuBarControl()
81            {
82              return JavaFXSafeProxyCreator.getMenuBarControl();
83            }
84        }
85  
86      static class MessageBusBeans
87        {
88          @Bean(name = APPLICATION_MESSAGE_BUS_BEAN_NAME)
89          public MessageBus applicationMessageBus()
90            {
91              final var executor = new ThreadPoolTaskExecutor();
92              executor.setWaitForTasksToCompleteOnShutdown(false);
93              executor.setThreadNamePrefix("messageBus-");
94              executor.setCorePoolSize(10);
95              executor.setMaxPoolSize(10);
96              executor.setQueueCapacity(10);
97              executor.afterPropertiesSet();
98              return new SimpleMessageBus(executor);
99            }
100       }
101 
102     public static final String APPLICATION_MESSAGE_BUS_BEAN_NAME = "applicationMessageBus";
103 
104     // Don't use Slf4j and its static logger - give Main a chance to initialize things
105     private final Logger log = LoggerFactory.getLogger(JavaFXSpringApplication.class);
106 
107     @Override @Nonnull
108     protected ConfigurableApplicationContext createApplicationContext()
109       {
110         final var mainClass = getClass();
111         final var componentClasses = new ArrayList<>(List.of(mainClass, Beans.class));
112 
113         if (getClass().isAnnotationPresent(EnableMessageBus.class))
114           {
115             log.info("Detected @{}, enabling message bus", EnableMessageBus.class.getSimpleName());
116             componentClasses.add(MessageBusBeans.class);
117           }
118 
119         log.info("Scanning beans from {}", mainClass);
120         return new AnnotationConfigApplicationContext(componentClasses.toArray(new Class<?>[0]));
121       }
122   }