Browse Source

mereg

master
hzzz 7 years ago
parent
commit
cad937bf23
  1. 2
      designer-base/src/com/fr/design/DesignerEnvManager.java
  2. 2
      designer-base/src/com/fr/design/actions/file/PreferencePane.java
  3. 4
      designer-base/src/com/fr/design/actions/help/WebDemoAction.java
  4. 9
      designer-base/src/com/fr/design/utils/DesignUtils.java
  5. 2
      designer-base/src/com/fr/start/BBSGuestPaneProvider.java
  6. 128
      designer-base/src/com/fr/start/ServerStarter.java
  7. 34
      designer-base/src/com/fr/start/SplashStrategy.java
  8. 56
      designer-base/src/com/fr/start/TomcatFRHost.java
  9. 15
      designer-base/src/com/fr/start/server/EmbedServerEvent.java
  10. 133
      designer-base/src/com/fr/start/server/FRTomcat.java
  11. 119
      designer-base/src/com/fr/start/server/FineEmbedServer.java
  12. 62
      designer-base/src/com/fr/start/server/MultiOutputStream.java
  13. 76
      designer-base/src/com/fr/start/server/ServerManageFrame.java
  14. 133
      designer-base/src/com/fr/start/server/ServerTray.java
  15. 280
      designer-base/src/com/fr/start/server/TomcatHost.java
  16. 18
      designer-base/src/com/fr/start/server/TomcatServerListener.java
  17. 6
      designer-chart/src/com/fr/van/chart/map/server/ChartMapEditorAction.java
  18. 31
      designer-realize/src/com/fr/start/Designer.java
  19. 142
      designer-realize/src/com/fr/start/SplashContext.java
  20. 210
      designer-realize/src/com/fr/start/fx/FastGifImage.java
  21. 211
      designer-realize/src/com/fr/start/fx/PrismImageLoader2.java
  22. 49
      designer-realize/src/com/fr/start/fx/SplashFx.java
  23. 133
      designer-realize/src/com/fr/start/fx/SplashFxWindow.java
  24. 69
      designer-realize/src/com/fr/start/jni/SplashJNI.java
  25. 87
      designer-realize/src/com/fr/start/jni/SplashMac.java
  26. BIN
      designer-realize/src/com/fr/start/jni/splash.dylib
  27. 4
      designer-realize/src/com/fr/start/module/DesignerEnvProvider.java
  28. 22
      designer-realize/src/com/fr/start/module/DesignerStartup.java
  29. 1
      designer-realize/src/com/fr/start/module/PreStartActivator.java

2
designer-base/src/com/fr/design/DesignerEnvManager.java

@ -740,7 +740,7 @@ public class DesignerEnvManager implements XMLReadable, XMLWriter {
/** /**
* 返回Jetty服务器的端口号 * 返回Jetty服务器的端口号
*/ */
public int getJettyServerPort() { public int getEmbedServerPort() {
return this.jettyServerPort; return this.jettyServerPort;
} }

2
designer-base/src/com/fr/design/actions/file/PreferencePane.java

@ -550,7 +550,7 @@ public class PreferencePane extends BasicPane {
this.pageLengthComboBox.setSelectedIndex(designerEnvManager.getPageLengthUnit()); this.pageLengthComboBox.setSelectedIndex(designerEnvManager.getPageLengthUnit());
this.reportLengthComboBox.setSelectedIndex(designerEnvManager.getReportLengthUnit()); this.reportLengthComboBox.setSelectedIndex(designerEnvManager.getReportLengthUnit());
this.portEditor.setValue(new Integer(designerEnvManager.getJettyServerPort())); this.portEditor.setValue(new Integer(designerEnvManager.getEmbedServerPort()));
this.jdkHomeTextField.setText(designerEnvManager.getJdkHome()); this.jdkHomeTextField.setText(designerEnvManager.getJdkHome());

4
designer-base/src/com/fr/design/actions/help/WebDemoAction.java

@ -4,7 +4,7 @@ import com.fr.base.BaseUtils;
import com.fr.design.actions.UpdateAction; import com.fr.design.actions.UpdateAction;
import com.fr.design.menu.MenuKeySet; import com.fr.design.menu.MenuKeySet;
import com.fr.general.Inter; import com.fr.general.Inter;
import com.fr.start.StartServer; import com.fr.start.ServerStarter;
import javax.swing.*; import javax.swing.*;
import java.awt.event.ActionEvent; import java.awt.event.ActionEvent;
@ -23,7 +23,7 @@ public class WebDemoAction extends UpdateAction {
* @param evt 事件 * @param evt 事件
*/ */
public void actionPerformed(ActionEvent evt) { public void actionPerformed(ActionEvent evt) {
StartServer.browserDemoURL(); ServerStarter.browserDemoURL();
} }
public static final MenuKeySet PRODUCT_DEMO = new MenuKeySet() { public static final MenuKeySet PRODUCT_DEMO = new MenuKeySet() {

9
designer-base/src/com/fr/design/utils/DesignUtils.java

@ -30,7 +30,7 @@ import com.fr.stable.CodeUtils;
import com.fr.stable.EncodeConstants; import com.fr.stable.EncodeConstants;
import com.fr.stable.StableUtils; import com.fr.stable.StableUtils;
import com.fr.stable.StringUtils; import com.fr.stable.StringUtils;
import com.fr.start.StartServer; import com.fr.start.ServerStarter;
import javax.swing.JOptionPane; import javax.swing.JOptionPane;
import javax.swing.SwingUtilities; import javax.swing.SwingUtilities;
@ -146,7 +146,7 @@ public class DesignUtils {
String line = null; String line = null;
while ((line = reader.readLine()) != null) { while ((line = reader.readLine()) != null) {
if (line.startsWith("demo")) { if (line.startsWith("demo")) {
StartServer.browserDemoURL(); ServerStarter.browserDemoURL();
} else if (StringUtils.isNotEmpty(line)) { } else if (StringUtils.isNotEmpty(line)) {
File f = new File(line); File f = new File(line);
String path = f.getAbsolutePath(); String path = f.getAbsolutePath();
@ -208,7 +208,6 @@ public class DesignUtils {
break; break;
} }
} }
EnvConfig oldEnv = EnvContext.currentEnv(); EnvConfig oldEnv = EnvContext.currentEnv();
String oldEnvPath = oldEnv == null ? null : oldEnv.getPath(); String oldEnvPath = oldEnv == null ? null : oldEnv.getPath();
@ -358,10 +357,10 @@ public class DesignUtils {
} else { } else {
try { try {
String web = GeneralContext.getCurrentAppNameOfEnv(); String web = GeneralContext.getCurrentAppNameOfEnv();
String url = "http://localhost:" + DesignerEnvManager.getEnvManager().getJettyServerPort() String url = "http://localhost:" + DesignerEnvManager.getEnvManager().getEmbedServerPort()
+ "/" + web + "/" + ServerConfig.getInstance().getServletName() + baseRoute + "/" + web + "/" + ServerConfig.getInstance().getServletName() + baseRoute
+ postfixOfUri; + postfixOfUri;
StartServer.browserURLWithLocalEnv(url); ServerStarter.browserURLWithLocalEnv(url);
} catch (Throwable e) { } catch (Throwable e) {
// //
} }

2
designer-base/src/com/fr/start/BBSGuestPaneProvider.java

@ -10,6 +10,6 @@ package com.fr.start;
*/ */
public interface BBSGuestPaneProvider { public interface BBSGuestPaneProvider {
public static final String XML_TAG = "BBSGuestPane"; String XML_TAG = "BBSGuestPane";
} }

128
designer-base/src/com/fr/start/StartServer.java → designer-base/src/com/fr/start/ServerStarter.java

@ -16,57 +16,43 @@ import com.fr.general.ComparatorUtils;
import com.fr.general.GeneralContext; import com.fr.general.GeneralContext;
import com.fr.general.Inter; import com.fr.general.Inter;
import com.fr.log.FineLoggerFactory; import com.fr.log.FineLoggerFactory;
import com.fr.stable.EnvChangedListener;
import com.fr.stable.OperatingSystem; import com.fr.stable.OperatingSystem;
import com.fr.stable.ProductConstants; import com.fr.stable.ProductConstants;
import com.fr.stable.StableUtils; import com.fr.stable.StableUtils;
import com.fr.stable.StringUtils; import com.fr.stable.StringUtils;
import com.fr.start.server.TomcatHost; import com.fr.start.server.FineEmbedServer;
import javax.swing.BorderFactory; import javax.swing.*;
import javax.swing.JOptionPane; import java.awt.*;
import java.awt.BorderLayout;
import java.awt.Desktop;
import java.awt.Font;
import java.io.IOException; import java.io.IOException;
import java.net.URI; import java.net.URI;
import java.net.URISyntaxException; import java.net.URISyntaxException;
public class StartServer { public class ServerStarter {
public static boolean NEED_LOAD_ENV = true;
// 原先的tomcatHost放在类TomcatHost里面,很不方便操作,而且因为存在多个进程的原因,
// 原先的getInstance()方法无多大意义
private static TomcatHost tomcatHost = null;
private static Object lock = new Object();
static {
GeneralContext.addEnvChangedListener(new EnvChangedListener() {
public void envChanged() {
currentEnvChanged();
}
});
}
/** /**
* 预览Demo * 预览Demo
* 找默认工作目录不应该按照名字去找而应该按照安装路径因为默认工作目录的名字可能会改变 * 找默认工作目录不应该按照名字去找而应该按照安装路径因为默认工作目录的名字可能会改变
*/ */
public static void browserDemoURL() { public static void browserDemoURL() {
if (FRContext.getCurrentEnv() instanceof RemoteEnv) { if (FRContext.getCurrentEnv() instanceof RemoteEnv) {
browser(FRContext.getCurrentEnv().getPath()); browser(FRContext.getCurrentEnv().getPath());
return; return;
} }
if (ComparatorUtils.equals(StableUtils.getInstallHome(), ".")) {//august:供代码使用 if (ComparatorUtils.equals(StableUtils.getInstallHome(), ".")) {//august:供代码使用
String web = GeneralContext.getCurrentAppNameOfEnv(); String web = GeneralContext.getCurrentAppNameOfEnv();
browserURLWithLocalEnv("http://localhost:" + DesignerEnvManager.getEnvManager().getJettyServerPort() + "/" + web + "/" + ServerConfig.getInstance().getServletName()); browserURLWithLocalEnv("http://localhost:" + DesignerEnvManager.getEnvManager().getEmbedServerPort() + "/" + web + "/" + ServerConfig.getInstance().getServletName());
return; return;
} }
DesignerEnvManager envManager = DesignerEnvManager.getEnvManager(); DesignerEnvManager envManager = DesignerEnvManager.getEnvManager();
if (!envManager.isCurrentEnvDefault()) { if (!envManager.isCurrentEnvDefault()) {
InformationPane inf = new InformationPane(envManager.getDefaultEnvName()); InformationPane inf = new InformationPane(envManager.getDefaultEnvName());
inf.showSmallWindow(DesignerContext.getDesignerFrame(), new DialogActionAdapter() { inf.showSmallWindow(DesignerContext.getDesignerFrame(), new DialogActionAdapter() {
@Override @Override
public void doOk() { public void doOk() {
try { try {
SignIn.signIn(DesignerEnvManager.getEnvManager().getDefaultEnv()); SignIn.signIn(DesignerEnvManager.getEnvManager().getDefaultEnv());
TemplateTreePane.getInstance().refreshDockingView(); TemplateTreePane.getInstance().refreshDockingView();
@ -84,56 +70,12 @@ public class StartServer {
} }
private static void initDemoServerAndBrowser() { private static void initDemoServerAndBrowser() {
synchronized (lock) {
if (tomcatHost != null) {
if (!tomcatHost.isDemoAppLoaded()) {
tomcatHost.exit();
tomcatHost = new TomcatHost(DesignerEnvManager.getEnvManager().getJettyServerPort());
tomcatHost.addAndStartInstallHomeWebApp();
}
} else {
tomcatHost = new TomcatHost(DesignerEnvManager.getEnvManager().getJettyServerPort());
tomcatHost.addAndStartInstallHomeWebApp();
}
}
try {
if (!tomcatHost.isStarted()) {
tomcatHost.start();
}
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage());
} finally {
//先访问Demo, 后访问报表, 不需要重置服务器.
NEED_LOAD_ENV = false;
browser("http://localhost:" + DesignerEnvManager.getEnvManager().getJettyServerPort() + "/" + GeneralContext.getCurrentAppNameOfEnv() + "/" + ServerConfig.getInstance().getServletName());
}
}
public static void start() {
try { try {
synchronized (lock) { FineEmbedServer.getInstance().start();
if (tomcatHost != null) {
if (NEED_LOAD_ENV) {
tomcatHost.exit();
tomcatHost = new TomcatHost(DesignerEnvManager.getEnvManager().getJettyServerPort());
tomcatHost.addAndStartLocalEnvHomeWebApp();
}
} else {
tomcatHost = new TomcatHost(DesignerEnvManager.getEnvManager().getJettyServerPort());
tomcatHost.addAndStartLocalEnvHomeWebApp();
}
if (!tomcatHost.isStarted()) {
tomcatHost.start();
}
}
} catch (InterruptedException e) {
FineLoggerFactory.getLogger().error(e.getMessage());
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage());
} finally { } finally {
NEED_LOAD_ENV = false; //先访问Demo, 后访问报表, 不需要重置服务器.
browser("http://localhost:" + DesignerEnvManager.getEnvManager().getEmbedServerPort() + "/" + GeneralContext.getCurrentAppNameOfEnv() + "/" + ServerConfig.getInstance().getServletName());
} }
} }
@ -143,25 +85,13 @@ public class StartServer {
* @param url 指定路径 * @param url 指定路径
*/ */
public static void browserURLWithLocalEnv(String url) { public static void browserURLWithLocalEnv(String url) {
start();
browser(url);
}
public static TomcatHost getInstance() {
// august: 正确的逻辑能保证jettyHost不为null,不然就有bug,不允许这儿加是否等于null判断
return tomcatHost;
}
/** FineEmbedServer.getInstance().start();
* 运行环境改变事件 browser(url);
*/
public static void currentEnvChanged() {
if (!NEED_LOAD_ENV) {
NEED_LOAD_ENV = true;
}
} }
private static void browser(String uri) { private static void browser(String uri) {
if (StringUtils.isEmpty(uri)) { if (StringUtils.isEmpty(uri)) {
FRContext.getLogger().info("The URL is empty!"); FRContext.getLogger().info("The URL is empty!");
return; return;
@ -180,6 +110,7 @@ public class StartServer {
} }
private static void startBrowserFromCommand(String uri, IOException e) { private static void startBrowserFromCommand(String uri, IOException e) {
if (OperatingSystem.isWindows()) { if (OperatingSystem.isWindows()) {
try { try {
// win10 内存用到到80%左右的时候, Desktop.browser经常提示"存储空间不足, 无法处理改命令", 用rundll32可以打开. // win10 内存用到到80%左右的时候, Desktop.browser经常提示"存储空间不足, 无法处理改命令", 用rundll32可以打开.
@ -193,29 +124,39 @@ public class StartServer {
} }
} }
public static boolean isStarted() {
return FineEmbedServer.getInstance().isRunning();
}
private static class InformationPane extends BasicPane { private static class InformationPane extends BasicPane {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = 1L;
private static final int FREE_STYLE_TOP = 15; private static final int FREE_STYLE_TOP = 15;
private static final int FREE_STYLE_OTHER = 5; private static final int FREE_STYLE_OTHER = 5;
public InformationPane(String message) { InformationPane(String message) {
init(message); init(message);
} }
private void init(String message) { private void init(String message) {
this.setLayout(new BorderLayout(10, 10)); this.setLayout(new BorderLayout(10, 10));
this.setBorder(BorderFactory.createEmptyBorder(FREE_STYLE_TOP, FREE_STYLE_OTHER, FREE_STYLE_OTHER, FREE_STYLE_OTHER)); this.setBorder(BorderFactory.createEmptyBorder(FREE_STYLE_TOP, FREE_STYLE_OTHER, FREE_STYLE_OTHER, FREE_STYLE_OTHER));
String text; String text;
if (!ComparatorUtils.equals(message, Inter.getLocText(new String[]{"Default", "Utils-Report_Runtime_Env"}))) { if (!ComparatorUtils.equals(message, Inter.getLocText(new String[]{"Default", "Utils-Report_Runtime_Env"}))) {
text = new StringBuffer(Inter.getLocText("FR-Designer_Open")) text = Inter.getLocText("FR-Designer_Open") +
.append(ProductConstants.APP_NAME) ProductConstants.APP_NAME +
.append(Inter.getLocText("FR-Designer_Utils-OpenDemoEnv")) Inter.getLocText("FR-Designer_Utils-OpenDemoEnv") +
.append(message).append(Inter.getLocText("FR-Designer_Utils-switch")).toString(); message + Inter.getLocText("FR-Designer_Utils-switch");
} else { } else {
text = new StringBuffer(Inter.getLocText("FR-Designer_Open")) text = Inter.getLocText("FR-Designer_Open") +
.append(ProductConstants.APP_NAME) ProductConstants.APP_NAME +
.append(Inter.getLocText("FR-Designer_Utils-NewDemoEnv")) Inter.getLocText("FR-Designer_Utils-NewDemoEnv") +
.append(message).append(Inter.getLocText("FR-Designer_Utils-switch")).toString(); message + Inter.getLocText("FR-Designer_Utils-switch");
} }
UITextArea a = new UITextArea(text); UITextArea a = new UITextArea(text);
a.setFont(new Font("Dialog", Font.PLAIN, 12)); a.setFont(new Font("Dialog", Font.PLAIN, 12));
@ -227,6 +168,7 @@ public class StartServer {
@Override @Override
protected String title4PopupWindow() { protected String title4PopupWindow() {
return Inter.getLocText("FR-Designer_Tooltips"); return Inter.getLocText("FR-Designer_Tooltips");
} }

34
designer-base/src/com/fr/start/SplashStrategy.java

@ -0,0 +1,34 @@
package com.fr.start;
/**
* 启动动画策略接口
*
* @author vito
* @date 2018/6/1
*/
public interface SplashStrategy {
/**
* 显示启动动画窗口
*/
void show();
/**
* 隐藏启动动画窗口
*/
void hide();
/**
* 设置模块加载信息
*
* @param text 更新的文字
*/
void updateModuleLog(String text);
/**
* 设置感谢文字
*
* @param text 更新的文字
*/
void updateThanksLog(String text);
}

56
designer-base/src/com/fr/start/TomcatFRHost.java

@ -1,56 +0,0 @@
package com.fr.start;
import java.io.File;
import javax.servlet.ServletException;
import org.apache.catalina.Context;
import org.apache.catalina.LifecycleException;
import org.apache.catalina.core.AprLifecycleListener;
import org.apache.catalina.core.StandardServer;
import org.apache.catalina.startup.Tomcat;
public class TomcatFRHost {
private static Tomcat tomcat;
public static Tomcat getTomcat() {
return tomcat;
}
private static StandardServer server;
private static AprLifecycleListener listener;
public static void main(String[] args) throws Exception {
tomcat = new Tomcat();
// 主机名,或ip
// tomcat.setHostname("localhost");
// 设置端口,80为默认端口
tomcat.setPort(8071);
// tomcat用于存储自身的信息,可以随意指定,最好包含在项目目录下
tomcat.setBaseDir(".");
// 建立server参照tomcat文件结构
server = (StandardServer) tomcat.getServer();
listener = new AprLifecycleListener();
server.addLifecycleListener(listener);
// 将appBase设为本项目所在目录
//tomcat.getHost().setAppBase(".");
tomcat.getHost().setAppBase(
System.getProperty("user.dir") + File.separator + ".");
// 第二个参数对应docBase为web应用路径,目录下应有WEB-INF,WEB-INF下要有web.xml
// 启动tomcat
try {
tomcat.start();
Context ct1 = tomcat.addWebapp("/WebReport", "/Users/momeak/Documents/Working/develop/others/tomcatsrc/WebReport");
} catch (LifecycleException e) {
e.printStackTrace();
} catch (ServletException e) {
e.printStackTrace();
}
// Context ct1 = tomcat.addWebapp("/examples", "/Users/momeak/Documents/Working/develop/others/tomcatsrc/examples");
// Context ct = tomcat.addWebapp("", "/Users/momeak/Documents/Working/develop/others/tomcatsrc/webapps/ROOT");
// tomcat.getServer().await();
System.out.println("启动成功");
}
}

15
designer-base/src/com/fr/start/server/EmbedServerEvent.java

@ -0,0 +1,15 @@
package com.fr.start.server;
import com.fr.event.Event;
import com.fr.event.Null;
/**
* Created by juhaoyu on 2018/6/5.
* 内置服务器事件
*/
public enum EmbedServerEvent implements Event<Null> {
BeforeStart,
AfterStart,
BeforeStop,
AfterStop
}

133
designer-base/src/com/fr/start/server/FRTomcat.java

@ -1,133 +0,0 @@
package com.fr.start.server;
import java.lang.reflect.InvocationTargetException;
import java.util.HashMap;
import java.util.Map;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.servlet.ServletException;
import org.apache.catalina.Context;
import org.apache.catalina.Host;
import org.apache.catalina.core.ContainerBase;
import org.apache.catalina.core.StandardContext;
import org.apache.catalina.core.StandardHost;
import org.apache.catalina.startup.ContextConfig;
import org.apache.catalina.startup.Tomcat;
public class FRTomcat extends Tomcat{
private final Map<String, Logger> frpinnedLoggers = new HashMap<String, Logger>();
private boolean frsilent = false;
public Context addWebapp(String contextPath, String docBase) throws ServletException {
silence(host, contextPath);
Context ctx = createContext(host, contextPath);
if (ctx instanceof StandardContext) {
((StandardContext)ctx).setDelegate(true);
}
ctx.setPath(contextPath);
ctx.setDocBase(docBase);
ctx.addLifecycleListener(new DefaultWebXmlListener());
ctx.setConfigFile(getWebappConfigFile(docBase, contextPath));
ContextConfig ctxCfg = new ContextConfig();
ctx.addLifecycleListener(ctxCfg);
ctxCfg.setDefaultWebXml(noDefaultWebXmlPath());
if (host == null) {
getHost().addChild(ctx);
} else {
host.addChild(ctx);
}
return ctx;
}
private void silence(Host host, String contextPath) {
String loggerName = getLoggerName(host, contextPath);
Logger logger = Logger.getLogger(loggerName);
frpinnedLoggers.put(loggerName, logger);
if (frsilent) {
logger.setLevel(Level.WARNING);
} else {
logger.setLevel(Level.INFO);
}
}
private String getLoggerName(Host host, String contextName) {
if (host == null) {
host = getHost();
}
StringBuilder loggerName = new StringBuilder();
loggerName.append(ContainerBase.class.getName());
loggerName.append(".[");
// Engine name
loggerName.append(host.getParent().getName());
loggerName.append("].[");
// Host name
loggerName.append(host.getName());
loggerName.append("].[");
// Context name
if (contextName == null || contextName.equals("")) {
loggerName.append("/");
} else if (contextName.startsWith("##")) {
loggerName.append("/");
loggerName.append(contextName);
}
loggerName.append(']');
return loggerName.toString();
}
private Context createContext(Host host, String url) {
String contextClass = StandardContext.class.getName();
if (host == null) {
host = this.getHost();
}
if (host instanceof StandardHost) {
contextClass = ((StandardHost) host).getContextClass();
}
try {
return (Context) Class.forName(contextClass).getConstructor()
.newInstance();
} catch (InstantiationException e) {
throw new IllegalArgumentException(
"Can't instantiate context-class " + contextClass
+ " for host " + host + " and url "
+ url, e);
} catch (IllegalAccessException e) {
throw new IllegalArgumentException(
"Can't instantiate context-class " + contextClass
+ " for host " + host + " and url "
+ url, e);
} catch (IllegalArgumentException e) {
throw new IllegalArgumentException(
"Can't instantiate context-class " + contextClass
+ " for host " + host + " and url "
+ url, e);
} catch (InvocationTargetException e) {
throw new IllegalArgumentException(
"Can't instantiate context-class " + contextClass
+ " for host " + host + " and url "
+ url, e);
} catch (NoSuchMethodException e) {
throw new IllegalArgumentException(
"Can't instantiate context-class " + contextClass
+ " for host " + host + " and url "
+ url, e);
} catch (SecurityException e) {
throw new IllegalArgumentException(
"Can't instantiate context-class " + contextClass
+ " for host " + host + " and url "
+ url, e);
} catch (ClassNotFoundException e) {
throw new IllegalArgumentException(
"Can't instantiate context-class " + contextClass
+ " for host " + host + " and url "
+ url, e);
}
}
}

119
designer-base/src/com/fr/start/server/FineEmbedServer.java

@ -0,0 +1,119 @@
package com.fr.start.server;
import com.fr.base.FRContext;
import com.fr.design.DesignerEnvManager;
import com.fr.event.EventDispatcher;
import com.fr.log.FineLoggerFactory;
import com.fr.module.ModuleRole;
import com.fr.stable.lifecycle.AbstractLifecycle;
import com.fr.startup.FineWebApplicationInitializer;
import com.fr.third.springframework.web.SpringServletContainerInitializer;
import com.fr.third.springframework.web.context.support.AnnotationConfigWebApplicationContext;
import org.apache.catalina.Context;
import org.apache.catalina.LifecycleException;
import org.apache.catalina.loader.VirtualWebappLoader;
import org.apache.catalina.startup.Tomcat;
import java.io.File;
import java.util.HashSet;
import java.util.Set;
/**
* Created by juhaoyu on 2018/6/5.
*/
public class FineEmbedServer extends AbstractLifecycle {
private static final FineEmbedServer INSTANCE = new FineEmbedServer();
private Tomcat tomcat;
public static FineEmbedServer getInstance() {
return INSTANCE;
}
private FineEmbedServer() {}
@Override
protected synchronized void executeStart() {
EventDispatcher.fire(EmbedServerEvent.BeforeStart);
try {
//初始化tomcat
initTomcat();
tomcat.start();
} catch (LifecycleException e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
EventDispatcher.fire(EmbedServerEvent.AfterStart);
}
private void initTomcat() {
tomcat = new Tomcat();
tomcat.setPort(DesignerEnvManager.getEnvManager().getEmbedServerPort());
String docBase = new File(FRContext.getCurrentEnv().getPath()).getParent();
String appName = "/" + FRContext.getCurrentEnv().getAppName();
Context context = tomcat.addContext(appName, docBase);
tomcat.addServlet(appName, "default", "org.apache.catalina.servlets.DefaultServlet");
//覆盖tomcat的WebAppClassLoader
context.setLoader(new FRTomcatLoader());
//直接指定initializer,tomcat就不用再扫描一遍了
SpringServletContainerInitializer initializer = new SpringServletContainerInitializer();
Set<Class<?>> classes = new HashSet<Class<?>>();
classes.add(FineWebApplicationInitializer.class);
context.addServletContainerInitializer(initializer, classes);
}
@Override
protected synchronized void executeStop() {
EventDispatcher.fire(EmbedServerEvent.BeforeStop);
try {
stopSpring();
stopServerActivator();
stopTomcat();
} catch (LifecycleException e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
EventDispatcher.fire(EmbedServerEvent.AfterStop);
}
private void stopServerActivator() {
ModuleRole.ServerRoot.stop();
}
private void stopSpring() {
AnnotationConfigWebApplicationContext context = ModuleRole.ServerRoot.getSingleton(AnnotationConfigWebApplicationContext.class);
if (context != null) {
context.stop();
context.destroy();
}
}
private void stopTomcat() throws LifecycleException {
tomcat.stop();
tomcat.destroy();
}
/**
* Created by juhaoyu on 2018/6/5.
* 自定义的tomcat loader主要用于防止内置服务器再加载一遍class
*/
private static class FRTomcatLoader extends VirtualWebappLoader {
@Override
public ClassLoader getClassLoader() {
return this.getClass().getClassLoader();
}
}
}

62
designer-base/src/com/fr/start/server/MultiOutputStream.java

@ -1,62 +0,0 @@
package com.fr.start.server;
import java.io.IOException;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List;
/**
* p: 这是为了将一个OutputStream输出多个OutputStream
*/
public class MultiOutputStream extends OutputStream {
private List outList = new ArrayList();
public MultiOutputStream() {
}
public void addOutputStream(OutputStream output) {
this.outList.add(output);
}
public void removeOutputStream(OutputStream output) {
this.outList.remove(output);
}
public int getOutputStreamCount() {
return this.outList.size();
}
public OutputStream getOutputStream(int index) {
return (OutputStream) this.outList.get(index);
}
public void write(int b) throws IOException {
for(int i = 0; i < outList.size(); i++) {
((OutputStream)outList.get(i)).write(b);
}
}
public void write(byte buff[]) throws IOException {
for(int i = 0; i < outList.size(); i++) {
((OutputStream)outList.get(i)).write(buff);
}
}
public void write(byte buff[], int off, int len) throws IOException {
for(int i = 0; i < outList.size(); i++) {
((OutputStream)outList.get(i)).write(buff, off, len);
}
}
public void flush() throws IOException {
for(int i = 0; i < outList.size(); i++) {
((OutputStream)outList.get(i)).flush();
}
}
public void close() throws IOException {
for(int i = 0; i < outList.size(); i++) {
((OutputStream)outList.get(i)).close();
}
}
}

76
designer-base/src/com/fr/start/server/ServerManageFrame.java

@ -1,27 +1,20 @@
package com.fr.start.server; package com.fr.start.server;
import java.awt.BorderLayout;
import java.awt.Desktop;
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.BorderFactory;
import javax.swing.JFrame;
import com.fr.base.FRContext;
import com.fr.design.gui.ilable.UILabel;
import javax.swing.JPanel;
import javax.swing.SwingConstants;
import com.fr.base.BaseUtils; import com.fr.base.BaseUtils;
import com.fr.base.FRContext;
import com.fr.design.gui.ibutton.UIButton; import com.fr.design.gui.ibutton.UIButton;
import com.fr.design.gui.ilable.UILabel;
import com.fr.design.gui.itextfield.UITextField; import com.fr.design.gui.itextfield.UITextField;
import com.fr.design.layout.FRGUIPaneFactory; import com.fr.design.layout.FRGUIPaneFactory;
import com.fr.general.Inter;
import com.fr.start.StartServer;
import com.fr.design.utils.DesignUtils; import com.fr.design.utils.DesignUtils;
import com.fr.design.utils.gui.GUICoreUtils; import com.fr.design.utils.gui.GUICoreUtils;
import com.fr.general.Inter;
import com.fr.start.ServerStarter;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
/** /**
* 内置Tomcat服务器管理界面 * 内置Tomcat服务器管理界面
@ -29,11 +22,11 @@ import com.fr.design.utils.gui.GUICoreUtils;
public class ServerManageFrame extends JFrame { public class ServerManageFrame extends JFrame {
// 由于实际情况,只需要一个当前对象的Instance. // 由于实际情况,只需要一个当前对象的Instance.
private static ServerManageFrame serverManageFrame = null; private static ServerManageFrame serverManageFrame = null;
private TomcatHost hostTomcatServer;
public static ServerManageFrame getServerManageFrame(TomcatHost hostTomcatServer) { static ServerManageFrame getServerManageFrame() {
if(serverManageFrame == null) {
serverManageFrame = new ServerManageFrame(hostTomcatServer); if (serverManageFrame == null) {
serverManageFrame = new ServerManageFrame();
} }
//p:每次启动之前都需要检查按钮的Enabled属性. //p:每次启动之前都需要检查按钮的Enabled属性.
@ -49,8 +42,7 @@ public class ServerManageFrame extends JFrame {
private JPanel startPane; private JPanel startPane;
private JPanel stopPane; private JPanel stopPane;
private ServerManageFrame(TomcatHost hostTomcatServer) { private ServerManageFrame() {
this.hostTomcatServer = hostTomcatServer;
DesignUtils.initLookAndFeel(); DesignUtils.initLookAndFeel();
this.setIconImage(BaseUtils.readImage("/com/fr/base/images/oem/trayStarted.png")); this.setIconImage(BaseUtils.readImage("/com/fr/base/images/oem/trayStarted.png"));
@ -82,12 +74,8 @@ public class ServerManageFrame extends JFrame {
startPane.add(new UILabel(Inter.getLocText("Server-Start"))); startPane.add(new UILabel(Inter.getLocText("Server-Start")));
startButton.addActionListener(new ActionListener() { startButton.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) { public void actionPerformed(ActionEvent e) {
TomcatHost tomcatServer = StartServer.getInstance();
try { try {
if(!tomcatServer.isStarted()) { FineEmbedServer.getInstance().start();
tomcatServer.start();
tomcatServer.addAndStartLocalEnvHomeWebApp();
}
checkButtonEnabled(); checkButtonEnabled();
} catch(Exception exp) { } catch(Exception exp) {
FRContext.getLogger().error(exp.getMessage()); FRContext.getLogger().error(exp.getMessage());
@ -103,11 +91,8 @@ public class ServerManageFrame extends JFrame {
stopPane.add(new UILabel(Inter.getLocText("Server-Stop"))); stopPane.add(new UILabel(Inter.getLocText("Server-Stop")));
stopButton.addActionListener(new ActionListener() { stopButton.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) { public void actionPerformed(ActionEvent e) {
TomcatHost tomcatServer = StartServer.getInstance();
try { try {
if(tomcatServer.isStarted()) { FineEmbedServer.getInstance().stop();
tomcatServer.stop();
}
checkButtonEnabled(); checkButtonEnabled();
} catch(Exception exp) { } catch(Exception exp) {
FRContext.getLogger().error(exp.getMessage()); FRContext.getLogger().error(exp.getMessage());
@ -125,24 +110,21 @@ public class ServerManageFrame extends JFrame {
infoPane.add(logPathTextField, BorderLayout.CENTER); infoPane.add(logPathTextField, BorderLayout.CENTER);
logPathTextField.setEditable(false); logPathTextField.setEditable(false);
// logfile
logPathTextField.setText(hostTomcatServer.getOutLogFile().getPath());
UIButton openButton = new UIButton(); UIButton openButton = new UIButton();
infoPane.add(openButton, BorderLayout.EAST); infoPane.add(openButton, BorderLayout.EAST);
openButton.setIcon(BaseUtils.readIcon("/com/fr/design/images/server/view.png")); openButton.setIcon(BaseUtils.readIcon("/com/fr/design/images/server/view.png"));
openButton.setToolTipText(Inter.getLocText("Open")); openButton.setToolTipText(Inter.getLocText("Open"));
openButton.addActionListener(new ActionListener() { // openButton.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) { // public void actionPerformed(ActionEvent evt) {
//
Desktop desktop = Desktop.getDesktop(); // Desktop desktop = Desktop.getDesktop();
try { // try {
desktop.open(ServerManageFrame.this.hostTomcatServer.getOutLogFile()); // desktop.open();
} catch(Exception exp) { // } catch(Exception exp) {
FRContext.getLogger().error(exp.getMessage()); // FRContext.getLogger().error(exp.getMessage());
} // }
} // }
}); // });
this.setSize(420, 160); this.setSize(420, 160);
this.setTitle(Inter.getLocText("Server-Embedded_Server")); this.setTitle(Inter.getLocText("Server-Embedded_Server"));
@ -154,8 +136,8 @@ public class ServerManageFrame extends JFrame {
* @throws Exception 异常 * @throws Exception 异常
*/ */
public void checkButtonEnabled() throws Exception { public void checkButtonEnabled() throws Exception {
TomcatHost tomcatServer = StartServer.getInstance();
if(tomcatServer.isStarted()) { if (ServerStarter.isStarted()) {
GUICoreUtils.setEnabled(startPane, false); GUICoreUtils.setEnabled(startPane, false);
GUICoreUtils.setEnabled(stopPane, true); GUICoreUtils.setEnabled(stopPane, true);
} else { } else {

133
designer-base/src/com/fr/start/server/ServerTray.java

@ -1,51 +1,46 @@
package com.fr.start.server; package com.fr.start.server;
import java.awt.AWTException; import com.fr.base.BaseUtils;
import java.awt.Image; import com.fr.base.FRContext;
import java.awt.MenuItem; import com.fr.general.Inter;
import java.awt.PopupMenu;
import java.awt.SystemTray; import java.awt.*;
import java.awt.TrayIcon;
import java.awt.event.ActionEvent; import java.awt.event.ActionEvent;
import java.awt.event.ActionListener; import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter; import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent; import java.awt.event.MouseEvent;
import com.fr.base.BaseUtils;
import com.fr.base.FRContext;
import com.fr.general.Inter;
import com.fr.start.StartServer;
/** /**
* Create server tray. * Create server tray.
*/ */
public class ServerTray { public class ServerTray {
public static boolean JVM_EXIT_ON_TRAY_EXIT = false;
private MenuItem manangeMenu, startMenu, stopMenu, exitMenu; private static ServerTray INSTANCE;
private Image trayStartedImage = BaseUtils.readImage(
"/com/fr/base/images/oem/trayStarted.png");
private Image trayStoppedImage = BaseUtils.readImage(
"/com/fr/base/images/oem/trayStopped.png");
private ServerManageFrame serverManageFrame; private MenuItem startMenu;
private TrayIcon trayIcon; private MenuItem stopMenu;
private Image trayStartedImage = BaseUtils.readImage("/com/fr/base/images/oem/trayStarted.png");
private Image trayStoppedImage = BaseUtils.readImage("/com/fr/base/images/oem/trayStopped.png");
private TomcatHost hostTomcatServer; private ServerManageFrame serverManageFrame;
private TrayIcon trayIcon;
public ServerTray(TomcatHost hostTomcatServer) {
this.hostTomcatServer = hostTomcatServer; public ServerTray() {
//p:首先构建右键菜单 //p:首先构建右键菜单
PopupMenu popup = new PopupMenu(); PopupMenu popup = new PopupMenu();
manangeMenu = new MenuItem(Inter.getLocText("Server-Open_Service_Manager")); MenuItem manangeMenu = new MenuItem(Inter.getLocText("Server-Open_Service_Manager"));
manangeMenu.addActionListener(new ActionListener() { manangeMenu.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) { public void actionPerformed(ActionEvent e) {
serverManageFrame = ServerManageFrame.getServerManageFrame(ServerTray.this.hostTomcatServer);
if(!serverManageFrame.isVisible()) { serverManageFrame = ServerManageFrame.getServerManageFrame();
if (!serverManageFrame.isVisible()) {
serverManageFrame.setVisible(true); serverManageFrame.setVisible(true);
} }
serverManageFrame.toFront();//p:到第一个. serverManageFrame.toFront();//p:到第一个.
@ -53,29 +48,24 @@ public class ServerTray {
}); });
startMenu = new MenuItem(Inter.getLocText("FR-Server_Embedded_Server_Start")); startMenu = new MenuItem(Inter.getLocText("FR-Server_Embedded_Server_Start"));
stopMenu = new MenuItem(Inter.getLocText("FR-Server_Embedded_Server_Stop")); stopMenu = new MenuItem(Inter.getLocText("FR-Server_Embedded_Server_Stop"));
exitMenu = new MenuItem(Inter.getLocText("Exit")); MenuItem exitMenu = new MenuItem(Inter.getLocText("Exit"));
//创建打开监听器 //创建打开监听器
ActionListener startListener = new ActionListener() { ActionListener startListener = new ActionListener() {
public void actionPerformed(ActionEvent e) { public void actionPerformed(ActionEvent e) {
TomcatHost tomcatServer = StartServer.getInstance();
try { try {
if(!tomcatServer.isStarted()) { FineEmbedServer.getInstance().start();
tomcatServer.start(); } catch (Exception exp) {
tomcatServer.addAndStartLocalEnvHomeWebApp();//暂停后再打开Tomcat,需要addApp
}
} catch(Exception exp) {
FRContext.getLogger().error(exp.getMessage(), exp); FRContext.getLogger().error(exp.getMessage(), exp);
} }
} }
}; };
ActionListener stopListener = new ActionListener() { ActionListener stopListener = new ActionListener() {
public void actionPerformed(ActionEvent e) { public void actionPerformed(ActionEvent e) {
TomcatHost tomcatServer = StartServer.getInstance();
try { try {
if(tomcatServer.isStarted()) { FineEmbedServer.getInstance().stop();
tomcatServer.stop(); } catch (Throwable exp) {
}
} catch(Exception exp) {
FRContext.getLogger().error(exp.getMessage(), exp); FRContext.getLogger().error(exp.getMessage(), exp);
} }
} }
@ -106,17 +96,17 @@ public class ServerTray {
return; return;
} }
ServerManageFrame serverManageFrame = ServerManageFrame.getServerManageFrame(ServerTray.this.hostTomcatServer); ServerManageFrame serverManageFrame = ServerManageFrame.getServerManageFrame();
if(!serverManageFrame.isVisible()) { if (!serverManageFrame.isVisible()) {
serverManageFrame.setVisible(true); serverManageFrame.setVisible(true);
} }
serverManageFrame.toFront();//p:到第一个. serverManageFrame.toFront();//p:到第一个.
} }
}); });
TrayIcon[] ti = SystemTray.getSystemTray().getTrayIcons(); TrayIcon[] icons = SystemTray.getSystemTray().getTrayIcons();
for(int i = 0;i <ti.length; i++){ for (TrayIcon icon : icons) {
SystemTray.getSystemTray().remove(ti[i]); SystemTray.getSystemTray().remove(icon);
} }
try { try {
@ -125,65 +115,18 @@ public class ServerTray {
System.err.println("Can not create the System Tray:" + e); System.err.println("Can not create the System Tray:" + e);
} }
//p:先check checkPopupMenuItemEnabled();
checkPopupMenuItemEnabled(this.hostTomcatServer);
// TODOJ
this.hostTomcatServer.addListener(new MyTomcatListner());
try {
if (!this.hostTomcatServer.isStarted()) {
this.hostTomcatServer.start();
}
} catch (Exception e){
FRContext.getLogger().error(e.getMessage(), e);
}
} }
private void exit() { private void exit() {
if (hostTomcatServer != null) {
try {
if(hostTomcatServer.isStarted()) {
hostTomcatServer.exit();
}
} catch(Exception exp) {
FRContext.getLogger().error(exp.getMessage(), exp);
}
hostTomcatServer = null;
}
FineEmbedServer.getInstance().stop();
SystemTray.getSystemTray().remove(trayIcon); SystemTray.getSystemTray().remove(trayIcon);
if (JVM_EXIT_ON_TRAY_EXIT) {
System.exit(0);
}
} }
class MyTomcatListner implements TomcatServerListener { private void checkPopupMenuItemEnabled() {
/**
* Started
*/
public void started(TomcatHost tomcatServer) {
checkPopupMenuItemEnabled(tomcatServer);
}
/**
* Stopped
*/
public void stopped(TomcatHost tomcatServer) {
checkPopupMenuItemEnabled(tomcatServer);
}
@Override
public void exited(TomcatHost tomcatServer) {
exit();
}
}
private void checkPopupMenuItemEnabled(TomcatHost tomcatServer) {
try { try {
if(tomcatServer.isStarted()) { if (FineEmbedServer.getInstance().isRunning()) {
startMenu.setEnabled(false); startMenu.setEnabled(false);
stopMenu.setEnabled(true); stopMenu.setEnabled(true);
@ -204,4 +147,8 @@ public class ServerTray {
} }
} }
public static void init() {
INSTANCE = new ServerTray();
}
} }

280
designer-base/src/com/fr/start/server/TomcatHost.java

@ -1,280 +0,0 @@
package com.fr.start.server;
import com.fr.module.ModuleContext;
import java.awt.SystemTray;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintStream;
import java.lang.reflect.Field;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import com.fr.general.GeneralContext;
import com.fr.stable.ProductConstants;
import org.apache.catalina.Context;
import org.apache.catalina.LifecycleException;
import org.apache.catalina.Server;
import org.apache.catalina.core.AprLifecycleListener;
import org.apache.catalina.core.StandardServer;
import com.fr.base.Env;
import com.fr.base.FRContext;
import com.fr.dav.LocalEnv;
import com.fr.design.DesignerEnvManager;
import com.fr.general.Inter;
import com.fr.stable.StableUtils;
import com.fr.stable.project.ProjectConstants;
import com.fr.start.StartServer;
public class TomcatHost {
private static FRTomcat tomcat;
private StandardServer server;
private AprLifecycleListener listener;
// private Server server;
private MultiOutputStream multiOutputStream = null;
private File outLogFile = null;
private int currentPort = -1;
// 内置服务器一个端口下面可以有多个应用,但是content不能重名
private Map<String, Context> webAppsMap = new HashMap<String, Context>();
private List<TomcatServerListener> listenerList = new ArrayList<TomcatServerListener>();
private boolean isDemoAppLoaded = false;
public TomcatHost(int port) {
this.currentPort = port;
initServer();
initLogFileAndOutputStream();
// TODO: 将HostTomcatServer放到ServerTray中去
tryStartServerTray();
}
public static FRTomcat getTomcat() {
return tomcat;
}
private void initServer() {
try {
//直接用自定义的,不用server.xml
this.tomcat = new FRTomcat();
this.tomcat.setPort(this.currentPort);
this.tomcat.setBaseDir(StableUtils.getInstallHome());
this.server = (StandardServer) tomcat.getServer();
this.listener = new AprLifecycleListener();
this.server.addLifecycleListener(listener);
this.tomcat.getHost().setAppBase(StableUtils.getInstallHome() + File.separator + ".");
this.tomcat.getConnector().setURIEncoding("UTF-8");
} catch (Exception e) {
//todo 最好加一个用server.xml
FRContext.getLogger().error(e.getMessage(), e);
}
}
private void initLogFileAndOutputStream() {
// log文件放置的位置
File logDir = null;
String installHome = StableUtils.getInstallHome();
if (installHome == null) {// 没有installHome的时候,就放到user.home下面喽
logDir = new File(ProductConstants.getEnvHome() + File.separator + ProjectConstants.LOGS_NAME);
} else {
// james:logs放在安装目录下面
logDir = new File(installHome + File.separator + ProjectConstants.LOGS_NAME + File.separator + "tomcat");
}
StableUtils.mkdirs(logDir);
DateFormat fateFormat = new SimpleDateFormat("yyyy-MM-dd");
Calendar curCalendar = Calendar.getInstance();
outLogFile = new File(logDir, "tomcat_" + fateFormat.format(curCalendar.getTime()) + ".log");
try {
multiOutputStream = new MultiOutputStream();
multiOutputStream.addOutputStream(new FileOutputStream(outLogFile, true));
multiOutputStream.addOutputStream(System.out);
System.setErr(new PrintStream(multiOutputStream));
System.setOut(new PrintStream(multiOutputStream));
} catch (IOException ioe) {
FRContext.getLogger().error(ioe.getMessage(), ioe);
}
}
private synchronized void addWebApplication(String context, String webappsPath) {
FRContext.getLogger().info("The new Application Path is: \n" + webappsPath + ", it will be added.");
if (webAppsMap.get(context) != null) {
Context webapp = webAppsMap.remove(context);
}
try {
if (!isStarted()) {
start();
}
Context webapp = tomcat.addWebapp(context, webappsPath);
webAppsMap.put(context, webapp);
} catch (Exception e) {
FRContext.getLogger().error(e.getMessage(), e);
}
}
private void addAndStartWebApplication(String context, String webAppPath) {
addWebApplication(context, webAppPath);
}
/**
* Get MultiOutputStream.
*/
public MultiOutputStream getMultiOutputStream() {
return this.multiOutputStream;
}
/**
* Get out log file
*/
public File getOutLogFile() {
return this.outLogFile;
}
private Server getServer() {
if (server == null) {
initServer();
}
return server;
}
/**
* Start
*
* @throws Exception
*/
public void start() throws Exception {
tomcat.start();
for (int i = 0; i < listenerList.size(); i++) {
TomcatServerListener listener = TomcatHost.this.getLinstener(i);
listener.started(this);
}
}
/**
* Stop
*
* @throws Exception
*/
public void stop() throws Exception {
tomcat.stop();
for (int i = 0; i < listenerList.size(); i++) {
TomcatServerListener listener = this.getLinstener(i);
listener.stopped(this);
}
StartServer.currentEnvChanged();
server = null;//重置server
}
/**
* Is started
*
* @throws Exception
*/
public boolean isStarted() throws Exception {
return getServer().getState().isAvailable();
}
public void addListener(TomcatServerListener listener) {
this.listenerList.add(listener);
}
public int getLinstenerCount() {
return this.listenerList.size();
}
public TomcatServerListener getLinstener(int index) {
if (index < 0 || index >= this.getLinstenerCount()) {
return null;
}
return this.listenerList.get(index);
}
public void clearLinsteners() {
this.listenerList.clear();
}
/**
* 尝试启动系统托盘
*/
private void tryStartServerTray() {
if (SystemTray.isSupported()) {
new ServerTray(this);
} else {
FRContext.getLogger().error("Do not support the SystemTray!");
}
}
public void exit() {
try {
getServer().stop();
} catch (LifecycleException e) {
FRContext.getLogger().error(e.getMessage(), e);
}
for (int i = 0; i < listenerList.size(); i++) {
TomcatServerListener listener = this.getLinstener(i);
listener.exited(this);
}
try {
getServer().destroy();
} catch (LifecycleException e) {
FRContext.getLogger().error(e.getMessage(), e);
}
StartServer.currentEnvChanged();
}
public int getCurrentPort() {
return currentPort;
}
/**
* 安装目录下的默认的WebReport这个只执行一次,除了预览demo其他的不要调用这个方法
*/
public void addAndStartInstallHomeWebApp() {
if (!isDemoAppLoaded) {
String installHome = StableUtils.getInstallHome();
String webApplication = StableUtils.pathJoin(new String[]{installHome, ProjectConstants.WEBAPP_NAME});
if (new File(webApplication).isDirectory()) {
addAndStartWebApplication("/" + ProjectConstants.WEBAPP_NAME, webApplication);
}
}
isDemoAppLoaded = true;
}
/**
* 加载Env下的报表运行环境
*/
public void addAndStartLocalEnvHomeWebApp() {
String name = DesignerEnvManager.getEnvManager().getCurEnvName();
if (name.equals(Inter.getLocText("Default"))) {
isDemoAppLoaded = true;
}
Env env = FRContext.getCurrentEnv();
if (env instanceof LocalEnv) {
String webApplication = new File(env.getPath()).getParent();
FRContext.getLogger().info(Inter.getLocText("INFO-Reset_Webapp") + ":" + webApplication);
addAndStartWebApplication("/" + GeneralContext.getCurrentAppNameOfEnv(), webApplication);
}
}
public boolean isDemoAppLoaded() {
return isDemoAppLoaded;
}
}

18
designer-base/src/com/fr/start/server/TomcatServerListener.java

@ -1,18 +0,0 @@
package com.fr.start.server;
public interface TomcatServerListener {
/**
* Started
*/
public void started(TomcatHost tomcatServer);
/**
* Stopped
*/
public void stopped(TomcatHost tomcatServer);
/**
* Exited
*/
public void exited(TomcatHost tomcatServer);
}

6
designer-chart/src/com/fr/van/chart/map/server/ChartMapEditorAction.java

@ -8,7 +8,7 @@ import com.fr.design.actions.UpdateAction;
import com.fr.general.GeneralContext; import com.fr.general.GeneralContext;
import com.fr.general.IOUtils; import com.fr.general.IOUtils;
import com.fr.general.Inter; import com.fr.general.Inter;
import com.fr.start.StartServer; import com.fr.start.ServerStarter;
import java.awt.event.ActionEvent; import java.awt.event.ActionEvent;
@ -23,11 +23,11 @@ public class ChartMapEditorAction extends UpdateAction {
} }
public void actionPerformed(ActionEvent evt) { public void actionPerformed(ActionEvent evt) {
int port = DesignerEnvManager.getEnvManager().getJettyServerPort(); int port = DesignerEnvManager.getEnvManager().getEmbedServerPort();
String web = GeneralContext.getCurrentAppNameOfEnv(); String web = GeneralContext.getCurrentAppNameOfEnv();
String serverlet = ServerConfig.getInstance().getReportServletName(); String serverlet = ServerConfig.getInstance().getReportServletName();
Env env = FRContext.getCurrentEnv(); Env env = FRContext.getCurrentEnv();
StartServer.browserURLWithLocalEnv(env.isLocalEnv() ? String.format("http://localhost:%d/%s/%s?op=map", port, web, serverlet) : env.getPath() + "?op=map"); ServerStarter.browserURLWithLocalEnv(env.isLocalEnv() ? String.format("http://localhost:%d/%s/%s?op=map", port, web, serverlet) : env.getPath() + "?op=map");
} }
} }

31
designer-realize/src/com/fr/start/Designer.java

@ -43,19 +43,21 @@ import com.fr.general.ComparatorUtils;
import com.fr.general.Inter; import com.fr.general.Inter;
import com.fr.module.Module; import com.fr.module.Module;
import com.fr.module.ModuleContext; import com.fr.module.ModuleContext;
import com.fr.stable.BuildContext;
import com.fr.stable.OperatingSystem;
import com.fr.stable.ProductConstants; import com.fr.stable.ProductConstants;
import com.fr.stable.StableUtils; import com.fr.stable.StableUtils;
import com.fr.stable.StringUtils; import com.fr.stable.StringUtils;
import com.fr.stable.xml.XMLTools; import com.fr.stable.xml.XMLTools;
import com.fr.start.fx.SplashFx;
import com.fr.start.jni.SplashMac;
import com.fr.start.module.StartupArgs; import com.fr.start.module.StartupArgs;
import com.fr.start.server.FineEmbedServer;
import com.fr.start.server.ServerTray;
import javax.swing.JComponent; import javax.swing.*;
import javax.swing.JPanel;
import javax.swing.border.MatteBorder; import javax.swing.border.MatteBorder;
import java.awt.Component; import java.awt.*;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Insets;
import java.awt.event.ActionEvent; import java.awt.event.ActionEvent;
import java.awt.event.ActionListener; import java.awt.event.ActionListener;
import java.io.File; import java.io.File;
@ -86,14 +88,29 @@ public class Designer extends BaseDesigner {
*/ */
public static void main(String[] args) { public static void main(String[] args) {
BuildContext.setBuildFilePath("/com/fr/stable/build.properties");
SplashContext.getInstance().registerSplash(createSplash());
SplashContext.getInstance().show();
Module designerRoot = ModuleContext.parseRoot("designer-startup.xml"); Module designerRoot = ModuleContext.parseRoot("designer-startup.xml");
//传递启动参数 //传递启动参数
designerRoot.setSingleton(StartupArgs.class, new StartupArgs(args)); designerRoot.setSingleton(StartupArgs.class, new StartupArgs(args));
designerRoot.start(); designerRoot.start();
if (FRContext.getCurrentEnv() instanceof LocalEnv) { if (FRContext.getCurrentEnv() instanceof LocalEnv) {
// 预启动一下 // 预启动一下
StartServer.start(); FineEmbedServer.getInstance().start();
ServerTray.init();
} }
}
private static SplashStrategy createSplash() {
// 这里可以开接口加载自定义启动画面
if (OperatingSystem.isWindows()) {
return new SplashFx();
} else if (OperatingSystem.isMacOS()) {
return new SplashMac();
}
return new SplashFx();
} }
public Designer(String[] args) { public Designer(String[] args) {

142
designer-realize/src/com/fr/start/SplashContext.java

@ -0,0 +1,142 @@
package com.fr.start;
import com.fr.base.FRContext;
import com.fr.design.mainframe.bbs.BBSConstants;
import com.fr.general.Inter;
import com.fr.stable.StringUtils;
import com.fr.stable.module.ModuleAdapter;
import com.fr.stable.module.ModuleListener;
import java.util.Locale;
import java.util.Random;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
/**
* 启动动画策略
*
* @author vito
* @date 2018/6/5
*/
public class SplashContext {
private static final SplashContext SPLASH_CONTEXT = new SplashContext();
private SplashStrategy splashStrategy;
private String moduleID = "";
private int loadingIndex = 0;
private String[] loading = new String[]{"..", "....", "......"};
private static final String GUEST = getRandomUser();
private ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);
private ModuleListener listener;
public static SplashContext getInstance() {
return SPLASH_CONTEXT;
}
private SplashContext() {
}
/**
* 注册具体的启动动画
*/
public void registerSplash(SplashStrategy splashStrategy) {
this.splashStrategy = splashStrategy;
}
/**
* 注册监听
*/
public ModuleListener getModuleListener() {
initListener();
return listener;
}
/**
* 展示启动动画
*/
public void show() {
splashStrategy.show();
}
/**
* 隐藏启动动画
*/
public void hide() {
splashStrategy.hide();
// 窗口关闭后取消定时获取模块信息的timer
scheduler.shutdown();
// 一次性
splashStrategy = null;
}
private void initListener() {
scheduler.scheduleAtFixedRate(new Runnable() {
@Override
public void run() {
loadingIndex++;
updateModuleLog(moduleID.isEmpty() ? StringUtils.EMPTY : moduleID + loading[loadingIndex % 3]);
}
}, 0, 300, TimeUnit.MILLISECONDS);
listener = new ModuleAdapter() {
@Override
public void onStartBefore(String moduleName, String moduleI18nName) {
moduleID = moduleI18nName;
loadingIndex++;
updateModuleLog(moduleID.isEmpty() ? StringUtils.EMPTY : moduleID + loading[loadingIndex % 3]);
}
};
showThanks();
}
private void updateModuleLog(String text) {
splashStrategy.updateModuleLog(text);
}
private void updateThanksLog(String text) {
splashStrategy.updateThanksLog(text);
}
/**
* 获取随机感谢人员
*/
private static String getRandomUser() {
String[] allGuest = BBSConstants.getAllGuest();
if (allGuest.length == 0) {
return StringUtils.EMPTY;
}
int num = new Random().nextInt(allGuest.length);
return StringUtils.BLANK + allGuest[num];
}
/**
* 展示感谢信息
*/
private void showThanks() {
if (shouldShowThanks()) {
updateThanksLog(Inter.getLocText("FR-Designer_Thanks-To") + GUEST);
}
}
/**
* 是否显示鸣谢面板
*/
private boolean shouldShowThanks() {
Locale[] hideLocales = {Locale.CHINA, Locale.TAIWAN};
for (Locale loc : hideLocales) {
if (FRContext.getLocale().equals(loc)) {
return true;
}
}
return false;
}
}

210
designer-realize/src/com/fr/start/fx/FastGifImage.java

@ -0,0 +1,210 @@
package com.fr.start.fx;
import com.sun.imageio.plugins.gif.GIFImageReader;
import com.sun.imageio.plugins.gif.GIFImageReaderSpi;
import com.sun.javafx.tk.ImageLoader;
import com.sun.javafx.tk.PlatformImage;
import javafx.animation.KeyFrame;
import javafx.animation.Timeline;
import javafx.event.Event;
import javafx.event.EventHandler;
import javafx.scene.image.WritableImage;
import javafx.util.Duration;
import javax.imageio.stream.FileImageInputStream;
import java.io.File;
import java.lang.ref.WeakReference;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.MalformedURLException;
import java.net.URI;
import java.net.URL;
import java.util.regex.Pattern;
/**
* 边加载边播放的gif加载器
*
* @author daniel
*/
public class FastGifImage extends WritableImage {
private String url;
private int gifCount;
public FastGifImage(String url, int w, int h) {
super(w, h);
this.url = validateUrl(url);
seekCount();
initialize();
}
/**
* 给出gif帧数加快加载速度
*
* @param url gif url
* @param gifCount gif帧数
* @param w
* @param h
*/
public FastGifImage(String url, int gifCount, int w, int h) {
super(w, h);
this.url = validateUrl(url);
this.gifCount = gifCount;
initialize();
}
private void seekCount() {
try {
GIFImageReaderSpi spi = new GIFImageReaderSpi();
GIFImageReader gifReader = (GIFImageReader) spi.createReaderInstance();
gifReader.setInput(new FileImageInputStream(new File(new URI(url))));
gifCount = gifReader.getNumImages(true);
} catch (Exception e) {
e.printStackTrace();
}
}
private static final Pattern URL_QUICKMATCH = Pattern.compile("^\\p{Alpha}[\\p{Alnum}+.-]*:.*$");
private static String validateUrl(final String url) {
if (url == null) {
throw new NullPointerException("URL must not be null");
}
if (url.trim().isEmpty()) {
throw new IllegalArgumentException("URL must not be empty");
}
try {
if (!URL_QUICKMATCH.matcher(url).matches()) {
final ClassLoader contextClassLoader = Thread.currentThread().getContextClassLoader();
URL resource;
if (url.charAt(0) == '/') {
resource = contextClassLoader.getResource(url.substring(1));
} else {
resource = contextClassLoader.getResource(url);
}
if (resource == null) {
throw new IllegalArgumentException("Invalid URL or resource not found");
}
return resource.toString();
}
// Use URL constructor for validation
return new URL(url).toString();
} catch (final IllegalArgumentException e) {
throw new IllegalArgumentException("Invalid URL" + e.getMessage());
} catch (final MalformedURLException e) {
throw new IllegalArgumentException("Invalid URL" + e.getMessage());
}
}
private void finishImage(Exception e) {
e.printStackTrace();
}
private void finishImage(ImageLoader loader) {
final Exception loadingException = loader.getException();
if (loadingException != null) {
finishImage(loadingException);
return;
}
initializeAnimatedImage(loader);
}
// Generates the animation Timeline for multiframe images.
private void initializeAnimatedImage(ImageLoader loader) {
animation = new Animation(this, loader);
animation.start();
}
// Support for animated images.
private Animation animation;
private static final class Animation {
final WeakReference<FastGifImage> imageRef;
final Timeline timeline;
final ImageLoader loader;
public Animation(final FastGifImage image, final ImageLoader loader) {
this.loader = loader;
imageRef = new WeakReference<FastGifImage>(image);
timeline = new Timeline();
timeline.setCycleCount(Timeline.INDEFINITE);
final int frameCount = loader.getFrameCount();
int duration = 0;
for (int i = 0; i < frameCount; ++i) {
addKeyFrame(i, duration);
duration = duration + loader.getFrameDelay(i);
}
// Note: we need one extra frame in the timeline to define how long
// the last frame is shown, the wrap around is "instantaneous"
addKeyFrame(0, duration);
}
public void start() {
timeline.play();
}
public void stop() {
timeline.stop();
}
private void updateImage(final int frameIndex) {
final FastGifImage image = imageRef.get();
if (image != null) {
image.setPlatformImagePropertyImpl(
loader.getFrame(frameIndex));
} else {
timeline.stop();
}
}
private void addKeyFrame(final int index, final double duration) {
timeline.getKeyFrames().add(
new KeyFrame(Duration.millis(duration),
new EventHandler() {
@Override
public void handle(Event event) {
updateImage(index);
}
}
));
}
}
private static Method method;
static {
try {
method = FastGifImage.class.getSuperclass().getSuperclass().getDeclaredMethod("platformImagePropertyImpl");
method.setAccessible(true);
} catch (Exception e) {
}
}
private void setPlatformImagePropertyImpl(PlatformImage image) {
try {
Object o = method.invoke(this);
Method method = o.getClass().getDeclaredMethod("set", Object.class);
method.setAccessible(true);
method.invoke(o, image);
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
} catch (NoSuchMethodException e) {
e.printStackTrace();
}
}
private void initialize() {
finishImage(new PrismImageLoader2(url, gifCount, (int) getRequestedWidth(), (int) getRequestedHeight(), isPreserveRatio(), isSmooth()));
}
}

211
designer-realize/src/com/fr/start/fx/PrismImageLoader2.java

@ -0,0 +1,211 @@
package com.fr.start.fx;
import com.sun.javafx.iio.ImageFrame;
import com.sun.javafx.iio.ImageLoadListener;
import com.sun.javafx.iio.ImageLoader;
import com.sun.javafx.iio.ImageMetadata;
import com.sun.javafx.iio.ImageStorageException;
import com.sun.javafx.iio.common.ImageTools;
import com.sun.javafx.iio.gif.GIFImageLoaderFactory;
import com.sun.javafx.tk.PlatformImage;
import com.sun.prism.Image;
import com.sun.prism.impl.PrismSettings;
import sun.util.logging.PlatformLogger;
import java.io.IOException;
import java.io.InputStream;
/**
* 边加载边播放的gif加载器
*
* @author daniel
*/
class PrismImageLoader2 implements com.sun.javafx.tk.ImageLoader {
private static PlatformLogger imageioLogger = null;
private Image[] images;
private int[] delayTimes;
private int width;
private int height;
private int gifCount = 1;
private Exception exception;
public PrismImageLoader2(final String url, int gifCount, final int width, final int height,
final boolean preserveRatio, final boolean smooth) {
this.gifCount = gifCount;
images = new Image[gifCount];
delayTimes = new int[gifCount];
this.width = width;
this.height = height;
new Thread() {
@Override
public void run() {
InputStream inputStream = null;
try {
inputStream = ImageTools.createInputStream(url);
loadAll(inputStream, width, height, preserveRatio, smooth);
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
inputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}.start();
}
@Override
public int getWidth() {
return width;
}
@Override
public int getHeight() {
return height;
}
@Override
public int getFrameCount() {
return gifCount;
}
@Override
public PlatformImage getFrame(int index) {
while (images[index] == null) {
synchronized (this) {
if (images[index] == null) {
try {
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
return images[index];
}
@Override
public int getFrameDelay(int index) {
// while (images[0] == null) {
// synchronized (this) {
// if(images[0] == null) {
// try {
// this.wait();
// } catch (InterruptedException e) {
// e.printStackTrace();
// }
// }
// }
// return 0;
// }
// return delayTimes[0];
// 直接使用第一帧的时间
return 40;
}
@Override
public int getLoopCount() {
return 0;
}
@Override
public Exception getException() {
return exception;
}
private void loadAll(InputStream stream, int w, int h,
boolean preserveRatio, boolean smooth) {
ImageLoadListener listener = new PrismLoadListener();
try {
ImageLoader loader = null;
loader = GIFImageLoaderFactory.getInstance().createImageLoader(stream);
loader.addListener(listener);
for (int i = 0; i < gifCount; i++) {
ImageFrame imageFrame = loader.load(i, w, h, preserveRatio, smooth);
images[i] = convert(imageFrame);
synchronized (this) {
this.notify();
}
}
} catch (ImageStorageException e) {
handleException(e);
} catch (Exception e) {
handleException(e);
}
}
private void handleException(final ImageStorageException isException) {
// unwrap ImageStorageException if possible
final Throwable exceptionCause = isException.getCause();
if (exceptionCause instanceof Exception) {
handleException((Exception) exceptionCause);
} else {
handleException((Exception) isException);
}
}
private void handleException(final Exception exception) {
if (PrismSettings.verbose) {
exception.printStackTrace(System.err);
}
this.exception = exception;
}
private Image convert(ImageFrame imgFrames) {
ImageFrame frame = imgFrames;
Image image = Image.convertImageFrame(frame);
ImageMetadata metadata = frame.getMetadata();
if (metadata != null) {
Integer delay = metadata.delayTime;
if (delay != null) {
delayTimes[0] = delay.intValue();
}
}
return image;
}
/**
* Returns the PlatformLogger for logging imageio-related activities.
*/
private static synchronized PlatformLogger getImageioLogger() {
if (imageioLogger == null) {
imageioLogger = PlatformLogger.getLogger("imageio");
}
return imageioLogger;
}
private class PrismLoadListener implements ImageLoadListener {
@Override
public void imageLoadWarning(ImageLoader loader, String message) {
getImageioLogger().warning(message);
}
@Override
public void imageLoadProgress(ImageLoader loader,
float percentageComplete) {
// progress only matters when backgroundLoading=true, but
// currently we are relying on AbstractRemoteResource for tracking
// progress of the InputStream, so there's no need to implement
// this for now; eventually though we might want to consider
// moving away from AbstractRemoteResource and instead use
// the built-in support for progress in the javafx-iio library...
}
@Override
public void imageLoadMetaData(ImageLoader loader, ImageMetadata metadata) {
// We currently have no need to listen for ImageMetadata ready.
}
}
}

49
designer-realize/src/com/fr/start/fx/SplashFx.java

@ -0,0 +1,49 @@
package com.fr.start.fx;
import com.fr.start.SplashStrategy;
import javafx.application.Application;
import javafx.application.Platform;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
/**
* JavaFx方式启动启动动画这种方式在mac下与
* swing一起启动会会出现线程死锁jvm等问题
* 所以这个方式仅用于windows上
*
* @author vito
* @date 2018/6/4
* @see com.fr.start.jni.SplashMac
*/
public class SplashFx implements SplashStrategy {
private SplashFxWindow test;
private static final ExecutorService SERVICE = Executors.newSingleThreadExecutor();
@Override
public void show() {
SERVICE.execute(new Runnable() {
@Override
public void run() {
Application.launch(SplashFxWindow.class);
}
});
test = SplashFxWindow.waitForStartUpTest();
}
@Override
public void hide() {
Platform.exit();
}
@Override
public void updateModuleLog(String text) {
test.updateModuleInfo(text);
}
@Override
public void updateThanksLog(String text) {
test.updateThanks(text);
}
}

133
designer-realize/src/com/fr/start/fx/SplashFxWindow.java

@ -0,0 +1,133 @@
package com.fr.start.fx;
import com.bulenkov.iconloader.util.JBUI;
import com.fr.base.FRContext;
import com.fr.stable.OperatingSystem;
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.scene.layout.AnchorPane;
import javafx.scene.paint.Color;
import javafx.scene.text.Font;
import javafx.scene.text.Text;
import javafx.stage.Stage;
import javafx.stage.StageStyle;
import java.util.concurrent.CountDownLatch;
/**
* JavaFx启动动画窗口
*
* @author vito
*/
public class SplashFxWindow extends Application {
private static float JBUI_INIT_SCALE = JBUI.scale(1f);
private static final String ARIAL_FONT_NAME = "Arial";
private static final String PF_FONT_NAME = "PingFang";
private static final String YAHEI_FONT_NAME = "Microsoft YaHei";
private static final int MODULE_INFO_LEFT_MARGIN = 36;
private static final int MODULE_INFO_BOTTOM_MARGIN = 28;
private static final int THINKS_BOTTOM_RIGHT = 35;
private static final int THINKS_BOTTOM_MARGIN = 27;
private static final int WINDOW_WIDTH = 640;
private static final int WINDOW_HEIGHT = 360;
private static final int FONT = 12;
private static final String THINKS_COLOR = "#82b1ce";
private static final CountDownLatch LATCH = new CountDownLatch(1);
private static SplashFxWindow app = null;
private Text moduleInfo;
private Text thanks;
private static int uiScale(int i) {
return (int) (i * JBUI_INIT_SCALE);
}
/**
* 获取当前运行实例黑科技
*
* @return 运行实例
*/
public static SplashFxWindow waitForStartUpTest() {
try {
LATCH.await();
} catch (InterruptedException e) {
FRContext.getLogger().error(e.getMessage(), e);
}
return app;
}
private static void setApp(SplashFxWindow window) {
app = window;
LATCH.countDown();
}
public SplashFxWindow() {
setApp(this);
}
@Override
public void start(Stage primaryStage) {
AnchorPane root = new AnchorPane();
primaryStage.initStyle(StageStyle.TRANSPARENT);
long t = System.currentTimeMillis();
Image image = new FastGifImage("com/fr/base/images/oem/splash_10.gif", 254, WINDOW_WIDTH, WINDOW_HEIGHT);
ImageView gif = new ImageView(image);
AnchorPane.setBottomAnchor(gif, 0d);
AnchorPane.setTopAnchor(gif, 0d);
AnchorPane.setLeftAnchor(gif, 0d);
AnchorPane.setRightAnchor(gif, 0d);
Font font;
if (OperatingSystem.isWindows()) {
font = new Font(YAHEI_FONT_NAME, uiScale(FONT));
} else if (OperatingSystem.isMacOS()) {
font = new Font(PF_FONT_NAME, uiScale(FONT));
} else {
font = new Font(ARIAL_FONT_NAME, uiScale(FONT));
}
moduleInfo = new Text();
moduleInfo.setFont(font);
moduleInfo.setFill(Color.WHITE);
AnchorPane.setLeftAnchor(moduleInfo, (double) uiScale(MODULE_INFO_LEFT_MARGIN));
AnchorPane.setBottomAnchor(moduleInfo, (double) uiScale(MODULE_INFO_BOTTOM_MARGIN));
thanks = new Text();
thanks.setFont(font);
thanks.setFill(Color.valueOf(THINKS_COLOR));
AnchorPane.setRightAnchor(thanks, (double) uiScale(THINKS_BOTTOM_RIGHT));
AnchorPane.setBottomAnchor(thanks, (double) uiScale(THINKS_BOTTOM_MARGIN));
root.getChildren().add(gif);
root.getChildren().add(moduleInfo);
root.getChildren().add(thanks);
Scene scene = new Scene(root, WINDOW_WIDTH, WINDOW_HEIGHT, null);
primaryStage.setScene(scene);
primaryStage.show();
}
/**
* 更新模块信息
*
* @param s 文字
*/
public void updateModuleInfo(String s) {
moduleInfo.setText(s);
}
/**
* 更新欢迎信息
*
* @param s 文字
*/
public void updateThanks(String s) {
thanks.setText(s);
}
}

69
designer-realize/src/com/fr/start/jni/SplashJNI.java

@ -0,0 +1,69 @@
package com.fr.start.jni;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
/**
* Splash JNI调用jni类改名或者移包之后
* 必须重新编译动态库
*
* @author vito
* @date 2018/6/4
*/
public class SplashJNI {
static {
try {
System.setProperty("java.library.path", ".");
System.loadLibrary("splash");
} catch (UnsatisfiedLinkError e) {
loadLibraryFromJar("/com/fr/start/jni/splash.dylib");
}
}
/**
* 显示启动动画窗口
*/
public native void show(String path);
/**
* 隐藏启动动画窗口
*/
public native void hide();
/**
* 设置模块加载信息
*/
public native void updateModuleLog(String text);
/**
* 设置感谢文字
*/
public native void updateThanksLog(String text);
/**
* 从jar中加载动态库
*
* @param path 路径/com/a/b
* @throws UnsatisfiedLinkError 没有找到合适的动态库
*/
private static void loadLibraryFromJar(String path) throws UnsatisfiedLinkError {
try (InputStream inputStream = SplashJNI.class.getResourceAsStream(path)) {
File tempLib = File.createTempFile(path, "");
byte[] buffer = new byte[1024];
int read = -1;
try (FileOutputStream fileOutputStream = new FileOutputStream(tempLib)) {
while ((read = inputStream.read(buffer)) != -1) {
fileOutputStream.write(buffer, 0, read);
}
}
System.load(tempLib.getAbsolutePath());
} catch (Exception e) {
throw new UnsatisfiedLinkError("Unable to open " + path + " from jar file.");
}
}
}

87
designer-realize/src/com/fr/start/jni/SplashMac.java

@ -0,0 +1,87 @@
package com.fr.start.jni;
import com.fr.stable.ProductConstants;
import com.fr.stable.StableUtils;
import com.fr.start.SplashContext;
import com.fr.start.SplashStrategy;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
/**
* mac上使用jni方式绘制gif不使用javafx有两个原因
* 1.mac上javafx和swing同时启动会导致卡死
* 2.platform.exit会导致设计器崩溃
*
* @author vito
* @see com.fr.start.fx.SplashFx
*/
public class SplashMac implements SplashStrategy {
private static final String SPLASH_CACHE_NAME = "splash_10.gif";
private static final String SPLASH_PATH = "/com/fr/base/images/oem/splash_10.gif";
private SplashJNI jni;
public SplashMac() {
jni = new SplashJNI();
}
/**
* 将jar中的资源拷贝到缓存文件夹
*
* @return 路径
* @throws IOException 拷贝失败
*/
private static String loadResFromJar() throws UnsatisfiedLinkError {
File tempLib = null;
try (InputStream inputStream = SplashContext.class.getResourceAsStream(SplashMac.SPLASH_PATH)) {
tempLib = new File(StableUtils.pathJoin(ProductConstants.getEnvHome(), SPLASH_CACHE_NAME));
byte[] buffer = new byte[1024];
int read = -1;
try (FileOutputStream fileOutputStream = new FileOutputStream(tempLib)) {
while ((read = inputStream.read(buffer)) != -1) {
fileOutputStream.write(buffer, 0, read);
}
}
return tempLib.getAbsolutePath();
} catch (IOException e) {
tempLib.deleteOnExit();
throw new UnsatisfiedLinkError("Unable to open " + SplashMac.SPLASH_PATH + " from jar file.");
}
}
@Override
public void show() {
if (jni != null) {
File splash = new File(StableUtils.pathJoin(ProductConstants.getEnvHome(), SPLASH_CACHE_NAME));
String path = splash.exists() ? splash.getAbsolutePath() : loadResFromJar();
jni.show(path);
}
}
@Override
public void hide() {
if (jni != null) {
jni.hide();
jni = null;
}
}
@Override
public void updateModuleLog(String text) {
if (jni != null) {
jni.updateModuleLog(text);
}
}
@Override
public void updateThanksLog(String text) {
if (jni != null) {
jni.updateThanksLog(text);
}
}
}

BIN
designer-realize/src/com/fr/start/jni/splash.dylib

Binary file not shown.

4
designer-realize/src/com/fr/start/module/DesignerEnvProvider.java

@ -28,7 +28,7 @@ import com.fr.file.filetree.FileNode;
import com.fr.general.ComparatorUtils; import com.fr.general.ComparatorUtils;
import com.fr.module.Activator; import com.fr.module.Activator;
import com.fr.start.EnvSwitcher; import com.fr.start.EnvSwitcher;
import com.fr.start.StartServer; import com.fr.start.ServerStarter;
import java.io.InputStream; import java.io.InputStream;
import java.io.OutputStream; import java.io.OutputStream;
@ -47,7 +47,7 @@ public class DesignerEnvProvider extends Activator {
for (String arg : args) { for (String arg : args) {
if (ComparatorUtils.equals(arg, "demo")) { if (ComparatorUtils.equals(arg, "demo")) {
DesignerEnvManager.getEnvManager().setCurrentEnv2Default(); DesignerEnvManager.getEnvManager().setCurrentEnv2Default();
StartServer.browserDemoURL(); ServerStarter.browserDemoURL();
break; break;
} }
} }

22
designer-realize/src/com/fr/start/module/DesignerStartup.java

@ -5,8 +5,7 @@ import com.fr.stable.CoreActivator;
import com.fr.stable.module.ModuleListener; import com.fr.stable.module.ModuleListener;
import com.fr.start.Designer; import com.fr.start.Designer;
import com.fr.start.EnvSwitcher; import com.fr.start.EnvSwitcher;
import com.fr.start.ReportSplashPane; import com.fr.start.SplashContext;
import com.fr.start.SplashWindow;
import com.fr.startup.activators.BasicActivator; import com.fr.startup.activators.BasicActivator;
/** /**
@ -16,12 +15,11 @@ public class DesignerStartup extends Activator {
@Override @Override
public void start() { public void start() {
startSub(PreStartActivator.class); startSub(PreStartActivator.class);
//启动基础部分 //启动基础部分
startSub(BasicActivator.class); startSub(BasicActivator.class);
//启动画面 //启动画面注册监听,必须在初始化国际化之后注册监听
SplashWindow splashWindow = createSplashWindow(); registerSplashListener();
String[] args = getModule().upFindSingleton(StartupArgs.class).get(); String[] args = getModule().upFindSingleton(StartupArgs.class).get();
Designer designer = new Designer(args); Designer designer = new Designer(args);
//启动env //启动env
@ -33,17 +31,15 @@ public class DesignerStartup extends Activator {
//启动设计器界面 //启动设计器界面
designer.show(args); designer.show(args);
//启动画面结束 //启动画面结束
splashWindow.setVisible(false); SplashContext.getInstance().hide();
splashWindow.dispose();
startSub(StartFinishActivator.class); startSub(StartFinishActivator.class);
} }
private SplashWindow createSplashWindow() { /**
* 注册启动动画监听器
ReportSplashPane reportSplashPane = new ReportSplashPane(); */
SplashWindow splashWindow = new SplashWindow(reportSplashPane); private void registerSplashListener() {
getModule().setSingleton(ModuleListener.class, reportSplashPane.getModuleListener()); getModule().setSingleton(ModuleListener.class, SplashContext.getInstance().getModuleListener());
return splashWindow;
} }
@Override @Override

1
designer-realize/src/com/fr/start/module/PreStartActivator.java

@ -25,7 +25,6 @@ public class PreStartActivator extends Activator {
public void start() { public void start() {
RestartHelper.deleteRecordFilesWhenStart(); RestartHelper.deleteRecordFilesWhenStart();
BuildContext.setBuildFilePath("/com/fr/stable/build.properties");
SiteCenter.getInstance(); SiteCenter.getInstance();
if (checkMultiStart()) { if (checkMultiStart()) {
return; return;

Loading…
Cancel
Save