帆软报表设计器源代码。
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

435 lines
14 KiB

package com.fr.design.actions.core;
import com.fr.base.Utils;
import com.fr.design.actions.UpdateAction;
import com.fr.design.file.HistoryTemplateListPane;
import com.fr.design.mainframe.JTemplate;
import com.fr.design.menu.MenuKeySet;
import com.fr.design.selection.QuickEditor;
import com.fr.design.ui.util.UIUtil;
import com.fr.log.FineLoggerFactory;
import com.fr.stable.StringUtils;
import com.fr.third.springframework.util.ReflectionUtils;
import javax.swing.Action;
import javax.swing.KeyStroke;
import java.awt.event.KeyEvent;
import java.lang.reflect.Constructor;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.CopyOnWriteArraySet;
/**
* 插入单元格元素和插入悬浮元素的一些集合方法
*
* @author null
* @version 2017年11月17日14点39分
*/
public class ActionFactory {
private static Set<Class<?>> actionClasses = new CopyOnWriteArraySet<>();
private static Set<Class<?>> floatActionClasses = new CopyOnWriteArraySet<>();
private static Class chartCollectionClass = null;
/**
* 无需每次实例化的悬浮元素编辑器
*/
private static ConcurrentMap<Class, QuickEditor> floatEditor = new ConcurrentHashMap<>();
/**
* 无需每次实例化的单元格元素编辑器
*/
private static ConcurrentMap<Class, QuickEditor> cellEditor = new ConcurrentHashMap<>();
/**
* 需要每次实例化的悬浮元素编辑器
*/
private static ConcurrentMap<Class, Class<? extends QuickEditor>> floatEditorClass = new ConcurrentHashMap<>();
/**
* 需要每次实例化的单元格元素编辑器
*/
private static ConcurrentMap<Class, Class<? extends QuickEditor>> cellEditorClass = new ConcurrentHashMap<>();
private static UpdateAction chartPreStyleAction = null;
private static UpdateAction chartEmptyDataStyleAction = null;
private static UpdateAction chartMapEditorAction = null;
private ActionFactory() {
}
/**
* 元素编辑器释放模板对象
*/
public static void editorRelease() {
for (Map.Entry<Class, QuickEditor> entry : cellEditor.entrySet()) {
entry.getValue().release();
}
for (Map.Entry<Class, QuickEditor> entry : floatEditor.entrySet()) {
entry.getValue().release();
}
}
/**
* 注册异步加载的单元格编辑器
* 首先放到 classMap 中,当初始化成功后,则移除,并放到 cellEditor 中
* 如果已经存在,则覆盖
*
* @param keyClazz 作为 key 的类
* @param editorClazz 作为 编辑器 的类
*/
public static void registerAsyncInitCellEditorClass(Class keyClazz, Class<? extends QuickEditor> editorClazz) {
cellEditorClass.put(keyClazz, editorClazz);
// 这里直接用 invokeLater 放到 UI 线程中去调用。
// 不阻塞主逻辑的启动
UIUtil.invokeLaterIfNeeded(new Runnable() {
@Override
public void run() {
try {
QuickEditor quickEditor = editorClazz.newInstance();
cellEditorClass.remove(keyClazz);
cellEditor.put(keyClazz, quickEditor);
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
}
});
}
/**
* 注册无需每次实例化的单元格元素编辑器
*
* @param clazz 单元格属性类型
* @param editor 单元格编辑器实例
*/
public static void registerCellEditor(Class clazz, QuickEditor editor) {
cellEditor.put(clazz, editor);
}
/**
* 注册无需每次实例化的悬浮元素编辑器
*
* @param clazz 悬浮元素类型
* @param editor 悬浮元素编辑器实例
*/
public static void registerFloatEditor(Class clazz, QuickEditor editor) {
floatEditor.put(clazz, editor);
}
/**
* 注册需要每次实例化的单元格元素编辑器
*
* @param clazz 单元格属性类型
* @param editorClass 单元格编辑器类
*/
public static void registerCellEditorClass(Class clazz, Class<? extends QuickEditor> editorClass) {
cellEditorClass.put(clazz, editorClass);
}
/**
* 注册需要每次实例化的悬浮元素编辑器
*
* @param clazz 悬浮元素类型
* @param editorClass 悬浮元素编辑器类
*/
public static void registerFloatEditorClass(Class clazz, Class<? extends QuickEditor> editorClass) {
floatEditorClass.put(clazz, editorClass);
}
/**
* kunsnat: 图表注册 悬浮元素编辑器 , 因为ChartCollecion和ChartQuickEditor一个在Chart,一个在Designer, 所以分开注册.
*
* @param clazz 待说明
*/
public static void registerChartCollection(Class clazz) {
chartCollectionClass = clazz;
}
/**
* 注册图表的 地图资源
*
* @param action 地图资源action
*/
public static void registerChartMapEditorAction(UpdateAction action) {
chartMapEditorAction = action;
}
/**
* 注册图表的 预定义样式.
*
* @param action 注册的图表预定义样式action
*/
public static void registerChartPreStyleAction(UpdateAction action) {
chartPreStyleAction = action;
}
/**
* 图表预定义样式Action
*
* @return 图表预定义样式Action
*/
public static UpdateAction getChartPreStyleAction() {
return chartPreStyleAction;
}
/**
* 图表编辑器Action
*
* @return 图表编辑器Action
*/
public static UpdateAction getChartMapEditorAction() {
return chartMapEditorAction;
}
/**
* 注册图表的 空数据提示样式.
*
* @param action 注册的图表空数据提示样式action
*/
public static void registerChartEmptyDataStyleAction(UpdateAction action) {
chartEmptyDataStyleAction = action;
}
/**
* 图表空数据提示样式Action
*
* @return 图表空数据提示样式Action
*/
public static UpdateAction getChartEmptyDataStyleAction() {
return chartEmptyDataStyleAction;
}
/**
* 获取图表集合类
*
* @return 获取图表集合类
*/
public static Class getChartCollectionClass() {
return chartCollectionClass;
}
/**
* 选中的悬浮元素的编辑器
*
* @param clazz 选中的悬浮元素类型
* @return 编辑器实例
*/
public static QuickEditor getFloatEditor(Class clazz) {
return createEditor(clazz, floatEditor, floatEditorClass);
}
/**
* 选中的单元格元素编辑器
*
* @param clazz 选中的单元格元素类型
* @return 编辑器实例
*/
public static QuickEditor getCellEditor(Class clazz) {
return createEditor(clazz, cellEditor, cellEditorClass);
}
public static UpdateAction createAction(Class clazz) {
try {
Constructor<? extends UpdateAction> c = clazz.getDeclaredConstructor();
ReflectionUtils.makeAccessible(c);
return c.newInstance();
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
return null;
}
/**
* peter:从Action来产生ToolTipText.
*
* @param action 动作
* @return 字符
*/
public static String createButtonToolTipText(Action action) {
StringBuffer buttonToolTipTextBuf = new StringBuffer();
//peter:把中文后面的(U),alt 快捷键的括号去掉,这个方法是临时的做法.
String actionName = (String) action.getValue(Action.NAME);
if (actionName.lastIndexOf("(") != -1) {
buttonToolTipTextBuf.append(actionName.substring(0, actionName.lastIndexOf("(")));
} else {
buttonToolTipTextBuf.append(actionName);
}
//peter:产生快捷键的ToolTip.
KeyStroke keyStroke = (KeyStroke) action.getValue(Action.ACCELERATOR_KEY);
if (keyStroke != null) {
buttonToolTipTextBuf.append(" (");
String modifiersText = KeyEvent.getKeyModifiersText(keyStroke.getModifiers());
if (!StringUtils.isEmpty(modifiersText)) {
buttonToolTipTextBuf.append(modifiersText);
buttonToolTipTextBuf.append('+');
}
buttonToolTipTextBuf.append(KeyEvent.getKeyText(keyStroke.getKeyCode()));
buttonToolTipTextBuf.append(')');
}
return Utils.objectToString(buttonToolTipTextBuf);
}
/**
* 纪录插入元素的种类
*
* @param cls 类型数组
*/
public static void registerCellInsertActionClass(Class<?>[] cls) {
if (cls != null) {
actionClasses.addAll(Arrays.asList(cls));
}
}
public static void referCellInsertActionClass(Class<?>[] cls) {
if (cls != null) {
actionClasses.clear();
actionClasses.addAll(Arrays.asList(cls));
}
}
/**
* 生成单元格插入相关的Action
* 表单中报表块编辑需要屏蔽掉"插入子报表"
*
* @param cls 构造函数参数类型
* @param obj 构造函数参数值
* @return 相关Action组成的一个数组
*/
public static UpdateAction[] createCellInsertAction(Class cls, Object obj) {
List<UpdateAction> actions = new ArrayList<>();
JTemplate jTemplate = HistoryTemplateListPane.getInstance().getCurrentEditingTemplate();
for (Class<?> clazz : actionClasses) {
if (clazz == null) {
continue;
}
if (jTemplate.acceptToolbarItem(clazz)) {
try {
Constructor<? extends UpdateAction> c = (Constructor<? extends UpdateAction>) clazz.getConstructor(cls);
actions.add(c.newInstance(obj));
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
}
}
return actions.toArray(new UpdateAction[actions.size()]);
}
public static MenuKeySet[] createCellInsertActionName() {
List<MenuKeySet> actionNames = new ArrayList<>();
JTemplate jTemplate = HistoryTemplateListPane.getInstance().getCurrentEditingTemplate();
for (Class<?> clazz : actionClasses) {
if (clazz == null) {
continue;
}
if (jTemplate.acceptToolbarItem(clazz)) {
try {
Constructor<? extends UpdateAction> c = (Constructor<? extends UpdateAction>) clazz.getConstructor();
actionNames.add(c.newInstance().getMenuKeySet());
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
}
}
return actionNames.toArray(new MenuKeySet[actionNames.size()]);
}
/**
* 登记悬浮元素插入类型
*
* @param cls 插入类型数组
*/
public static void registerFloatInsertActionClass(Class<?>[] cls) {
if (cls != null) {
floatActionClasses.addAll(Arrays.asList(cls));
}
}
public static void referFloatInsertActionClass(Class<?>[] cls) {
if (cls != null) {
floatActionClasses.clear();
floatActionClasses.addAll(Arrays.asList(cls));
}
}
/**
* 生成悬浮元素插入相关的Action
*
* @param cls 构造函数参数类型
* @param obj 构造函数参数值
* @return 相关Action组成的一个数组
*/
public static UpdateAction[] createFloatInsertAction(Class cls, Object obj) {
List<UpdateAction> actions = new ArrayList<>();
for (Class<?> clazz : floatActionClasses) {
if (clazz == null) {
continue;
}
try {
Constructor<? extends UpdateAction> c = (Constructor<? extends UpdateAction>) clazz.getConstructor(cls);
actions.add(c.newInstance(obj));
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
}
return actions.toArray(new UpdateAction[actions.size()]);
}
private static QuickEditor createEditor(Class clazz, Map<Class, QuickEditor> editorMap, Map<Class, Class<? extends QuickEditor>> editorClassMap) {
QuickEditor c = findQuickEditor(clazz, editorMap);
if (c == null) {
Class<? extends QuickEditor> cClazz = findQuickEditorClass(clazz, editorClassMap);
if (cClazz == null) {
FineLoggerFactory.getLogger().error("No Such Editor");
return null;
}
try {
Constructor<? extends QuickEditor> constructor = cClazz.getDeclaredConstructor();
ReflectionUtils.makeAccessible(constructor);
return constructor.newInstance();
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
return null;
}
return c;
}
private static QuickEditor findQuickEditor(Class clazz, Map<Class, QuickEditor> editorMap) {
QuickEditor c = editorMap.get(clazz);
if (c == null) {
Class superClazz = clazz.getSuperclass();
if (superClazz == null) {
return null;
}
return findQuickEditor(superClazz, editorMap);
}
return c;
}
private static Class<? extends QuickEditor> findQuickEditorClass(Class clazz, Map<Class, Class<? extends QuickEditor>> editorMap) {
Class<? extends QuickEditor> c = editorMap.get(clazz);
if (c == null) {
Class superClazz = clazz.getSuperclass();
if (superClazz == null) {
return null;
}
return findQuickEditorClass(superClazz, editorMap);
}
return c;
}
}