`

自己的通用的表格

 
阅读更多

建立了一个自己的通用的表格:

a)Comp为Table的父亲,在这个上面建table,class是要显示的实体类,ignoreList中,如果和class的filed名字一样就不建立这个列。
b)列隐藏伸展
c)显示默认就对应类的Field的toString
d)上下自动滚动。
e)Ctrl+鼠标滚动列。
f)当点击Table的其他位置的时候,就是没有Item的位置的时候,取消所以的选择。
g)列的Properties就是列的Class的Field。(还不知道Properties有用否)

代码:

public class MyTable {
	private static String 		RESTORE_COL_WIDTH 	= "restoredWidth";
	
	private TableViewer			v;
	private Table				t;
	private MenuManager 		tableContextMenu;
	private List<String> 		ignoreList;
	private List<String>		propertis;
	
	private Map<String,TableViewerColumn> columMap = new HashMap<String,TableViewerColumn>();

	/*
	 * for auto scroll
	 */
	private Runnable 	Heartbeat;
	private boolean 	Tracking;
	private int 		ScrollSpeed = 400;

	public MyTable(Composite comp, Class<?> clazz) {
		createTable(comp,clazz);
	}
	public MyTable(Composite comp, Class<?> clazz, List<String> ignoreList) {
		this.ignoreList = ignoreList;
		createTable(comp,clazz);
	}
	
	private void createTable(Composite comp, Class<?> clazz) {
		v = new TableViewer(comp, SWT.FULL_SELECTION | SWT.MULTI);
		t = v.getTable();
		t.setLinesVisible(true);
		t.setHeaderVisible(true);
		v.setContentProvider(new MyContentProvider());

		getPropertis(clazz);
		v.setColumnProperties(propertis.toArray(new String[0]));

		createColumn();
		setTableMenu();
		
		addVerticalAutoScroll();
		addCtrlScroll();
		addDesWhenNull();

		v.setInput(new TableData());
	}
	
	private void addDesWhenNull() {
		/*
		 * deselectAll when mouse click a space in table.
		 */
		t.addMouseListener(new MouseAdapter() {
			public void mouseDown(MouseEvent e) {
				if(t.getItem(new Point(e.x,e.y)) == null ) {
					t.deselectAll();
				}
			}
		});
	}
	private void addCtrlScroll() {
		t.addMouseWheelListener(new MouseWheelListener() {
			public void mouseScrolled(MouseEvent e) {
				if (e.stateMask == SWT.CTRL) {
					/*
					 * using getClientArea().width, hBar.getSelection(), e.count to calc
					 * which column to show.
					 * t.showColumn();
					 */
					
					ScrollBar hBar = t.getHorizontalBar();
					if(hBar != null) {
						TableColumn col = getShowColumn(hBar,e.count);
						if(col != null)
							t.showColumn(col);
					}
				}
			}

			private TableColumn getShowColumn(ScrollBar hBar, int count) {
				TableColumn col;
				TableColumn[] cols = t.getColumns();
				int totalWidth 	= t.getBounds().width;
				int hBarLeft 	= hBar.getSelection();
				int hBarRight 	= hBar.getMaximum() - hBar.getThumb() - hBar.getSelection();
				
				if(count > 0) {
					int colsWidth = 0 - hBarRight;
					for(int i=cols.length-1; i > -1; i--) {
						col = cols[i];
						colsWidth += col.getWidth();
						if(colsWidth > totalWidth)
							return col;
					}
				} else {
					int colsWidth = 0 - hBarLeft;
					for(int i=0; i < cols.length; i++) {
						col = cols[i];
						colsWidth += col.getWidth();
						if(colsWidth > totalWidth)
							return col;
					}
				}
				return null;
			}
		});
	}
	private void addVerticalAutoScroll() {
		/*
		 * swt.snippets.Snippet221
		 */
		
		Heartbeat = new Runnable() {
			public void run() {
				if(!Tracking || t.isDisposed()) return;
				Point cursor = Display.getCurrent().getCursorLocation();
				cursor = Display.getCurrent().map(null, t, cursor);
				Scroll(t, cursor);
				Display.getCurrent().timerExec(ScrollSpeed, Heartbeat);
			}

			private void Scroll(Table t, Point cursor) {
				TableItem item = t.getItem(cursor);
				if (item == null) return;
				int index = t.indexOf(item);
				if(index == 0 || index == t.getItemCount()-1)
					return;
				Rectangle area = t.getClientArea();
				int headerHeight = t.getHeaderHeight();
				int itemHeight= t.getItemHeight();
				if (cursor.y < area.y + headerHeight + 2 * itemHeight) {
					// mouse in the first or second item.
					index --;
				}
				if (cursor.y > area.y + area.height - 2 * itemHeight) {
					// mouse in the last first or second item.
					index ++;
				}
				if(index>-1 && index<t.getItemCount())
					t.showItem(t.getItem(index));
			}

		};
		Listener listener = new Listener() {
			public void handleEvent(Event event) {
				switch (event.type) {
				case SWT.MouseEnter:
					Tracking = true;
					Display.getCurrent().timerExec(0, Heartbeat);
					break;
				case SWT.MouseExit:
					Tracking = false;
					break;
				}
			}
		};
		t.addListener(SWT.MouseEnter, listener); 
		t.addListener(SWT.MouseExit, listener);
	}
	
	private void setTableMenu() {
		final MenuManager headerMenu = new MenuManager();
		addAction2HeaderMenu(headerMenu);

		t.addListener(SWT.MenuDetect, new Listener() {
			public void handleEvent(Event event) {
				Point pt = Display.getCurrent().map(null, t, new Point(event.x, event.y));
				Rectangle clientArea = t.getClientArea();
				boolean header = clientArea.y <= pt.y && pt.y < (clientArea.y + t.getHeaderHeight());
				if(header) {
					t.setMenu(headerMenu.createContextMenu(t));
				} else {
					if(tableContextMenu != null)
						t.setMenu(tableContextMenu.createContextMenu(t));
				}
			}
		});
	}

	private void addAction2HeaderMenu(MenuManager menu) {
		Action action;
		for(int i = 0; i < t.getColumnCount(); i++ ) {
			final TableColumn column = t.getColumn(i);
			action = new Action(t.getColumn(i).getText(),SWT.CHECK) {
				public void run() {
					if(!isChecked()) {
						ShrinkThread t = new ShrinkThread(column.getWidth(),column);
						t.run();
					} else {
						ExpandThread t = new ExpandThread(((Integer)column.getData(RESTORE_COL_WIDTH)).intValue(),column);
						t.run();
					}
				}
			};
			action.setChecked(true);
			menu.add(action);
		}
	}

	private void createColumn() {
		for(String property : propertis) {
			TableViewerColumn column = new TableViewerColumn(v, SWT.NONE);
			column.getColumn().setWidth(200);
			column.getColumn().setText(property);
			column.getColumn().setMoveable(true);
			
			column.setLabelProvider(new MyColumnLabelProvider(property));
			
			columMap.put(property, column);
		}
	}
	
	public List<String> getPropertis() {
		return propertis;
	}
	private void getPropertis(Class<?> clazz) {
		propertis = new ArrayList<String>();
		String name;
		for(Field f : clazz.getDeclaredFields()) {
			name = f.getName();
			if(!ignoreList.contains(name))
				propertis.add(f.getName());
		}
	}
	
	public void add(Object o) {
		((TableData)v.getInput()).add(o);
	}
	public void remove(Object o) {
		((TableData)v.getInput()).remove(o);
	}
	public void removeAll() {
		v.setInput(new TableData());
	}
	public void setColumnWidth(int width) {
		for(TableColumn col : v.getTable().getColumns())
			col.setWidth(width);
	}
	public void setColumnWidth(int[] widths) {
		int min = Math.min(widths.length, t.getColumnCount());
		for(int i=0; i<min; i++) {
			t.getColumn(i).setWidth(widths[i]);
		}
	}
	public void setColumnName(String[] names) {
		int min = Math.min(names.length, t.getColumnCount());
		for(int i=0; i<min; i++) {
			t.getColumn(i).setText(names[i]);
		}
	}
	public TableViewerColumn getTableViewerColumn(String property) {
		return columMap.get(property);
	}
	public void setColumnLabelProvider(String property,ColumnLabelProvider columnLabelProvider) {
		columMap.get(property).setLabelProvider(columnLabelProvider);
	}
	public void setContextMenu(MenuManager menu) {
		tableContextMenu = menu;
	}
	public TableViewer getTableViewer() {
		return v;
	}
	/**
	 * column shrink
	 */
	private class ShrinkThread extends Thread {

		private int width = 0;
		private TableColumn column;
		public ShrinkThread(int width, TableColumn column) {
			super();
			this.width = width;
			this.column = column;
		}
		public void run() {
			column.getDisplay().syncExec(new Runnable() {
				public void run() {
					column.setData(RESTORE_COL_WIDTH, new Integer(width));
				}
			});
			for(int i = width; i >= 0; i--) {
				final int index = i;
				column.getDisplay().syncExec(new Runnable() {
					public void run() {
						column.setWidth(index);
					}
				});
			}
			column.setResizable(false);
		}
	};

	/**
	 * column Expand
	 */
	private class ExpandThread extends Thread {
		private int width = 0;
		private TableColumn column;
		public ExpandThread(int width, TableColumn column) {
			super();
			this.width = width;
			this.column = column;
		}
		public void run() {
			for(int i = 0; i <= width; i++) {
				final int index = i;
				column.getDisplay().syncExec(new Runnable() {
					public void run() {
						column.setWidth(index);
					}
				});
			}
			column.setResizable(true);
		}
	}

	private class MyContentProvider implements IStructuredContentProvider ,PropertyChangeListener{
		private TableViewer viewer;
		
		public Object[] getElements(Object inputElement) {
			if(inputElement instanceof TableData)
				return ((TableData)inputElement).elements();
			return null;
		}
		public void dispose() {}
		public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
			this.viewer = (TableViewer) viewer;
			
			if (oldInput instanceof TableData)
				((TableData) oldInput).removePropertyChangeListener(this);
			if (newInput instanceof TableData) {
				((TableData) newInput).addPropertyChangeListener(this);
			}
		}
		
		public void propertyChange(PropertyChangeEvent event) {
			if (TableData.ADD_ELEMENT.equals(event.getPropertyName()))
				viewer.add(event.getNewValue());
			if (TableData.REMOVE_ELEMENT.equals(event.getPropertyName()))
				viewer.remove(event.getNewValue());
		}
	}
	private class MyColumnLabelProvider extends ColumnLabelProvider {
		private String FieldName;

		public MyColumnLabelProvider(String columnText) {
			super();
			this.FieldName = columnText;
		}

		public String getText(Object element) {
			Object o = getClassFieldContent(element, FieldName);
			return o == null ?"":o.toString();
		}

		private Object getClassFieldContent(Object obj, String fieldName) {
			Object o = null;
			for(Field f : obj.getClass().getDeclaredFields()) {
				if(f.getName().equals(fieldName)) {
					f.setAccessible(true);
					try {
						o = f.get(obj);
					} catch (IllegalArgumentException e) {
						e.printStackTrace();
					} catch (IllegalAccessException e) {
						e.printStackTrace();
					}
				}
			}
			return o;
		}
	}
}

abstract class ColumnViewerSorter extends ViewerComparator {
	public static final int ASC = 1;
	public static final int NONE = 0;
	public static final int DESC = -1;

	private int direction = 0;
	private TableViewerColumn column;
	private ColumnViewer viewer;

	private String property;

	public ColumnViewerSorter(ColumnViewer viewer, TableViewerColumn column, String property) {
		this.column = column;
		this.viewer = viewer;
		this.property = property;
		this.column.getColumn().addSelectionListener(new SelectionAdapter() {

			public void widgetSelected(SelectionEvent e) {
				if( ColumnViewerSorter.this.viewer.getComparator() != null ) {
					if( ColumnViewerSorter.this.viewer.getComparator() == ColumnViewerSorter.this ) {
						int tdirection = ColumnViewerSorter.this.direction;
						if( tdirection == ASC ) {
							setSorter(ColumnViewerSorter.this, DESC);
						} else if( tdirection == DESC ) {
							setSorter(ColumnViewerSorter.this, NONE);
						}
					} else {
						setSorter(ColumnViewerSorter.this, ASC);
					}
				} else {
					setSorter(ColumnViewerSorter.this, ASC);
				}
			}
		});
	}

	public void setSorter(ColumnViewerSorter sorter, int direction) {
		if( direction == NONE ) {
			column.getColumn().getParent().setSortColumn(null);
			column.getColumn().getParent().setSortDirection(SWT.NONE);
			viewer.setComparator(null);
		} else {
			column.getColumn().getParent().setSortColumn(column.getColumn());
			sorter.direction = direction;
			if( direction == ASC ) {
				column.getColumn().getParent().setSortDirection(SWT.DOWN);
			} else {
				column.getColumn().getParent().setSortDirection(SWT.UP);
			}
			if( viewer.getComparator() == sorter ) {
				viewer.refresh();
			} else {
				viewer.setComparator(sorter);
			}
		}
	}
	public int compare(Viewer viewer, Object e1, Object e2) {
		return direction * doCompare(e1, e2, property);
	}
	protected abstract int doCompare(Object e1, Object e2, String property);
}

 

 

表格数据类代码:

public class TableData {
	public static final String ADD_ELEMENT 		= "add Element";
	public static final String REMOVE_ELEMENT 	= "remove Element";

	private PropertyChangeSupport delegate;
	private Vector<Object> content;

	public TableData() {
		content = new Vector<Object>();
		delegate = new PropertyChangeSupport(this);
	}

	public void addPropertyChangeListener(PropertyChangeListener listener) {
		delegate.addPropertyChangeListener(listener);
	}

	public void firePropertyChange(PropertyChangeEvent event) {
		delegate.firePropertyChange(event);
	}

	public void removePropertyChangeListener(PropertyChangeListener listener) {
		delegate.removePropertyChangeListener(listener);
	}

	public void add(Object element) {
		if(content.contains(element))
			return;
		if(content.add(element))
			firePropertyChange(new PropertyChangeEvent(this, ADD_ELEMENT, null,	element));
	}

	public void remove(Object element) {
		if (content.remove(element))
			firePropertyChange(new PropertyChangeEvent(this, REMOVE_ELEMENT, null, element));
	}

	public Object[] elements() {
		return content.toArray();
	}

	public void printInfo() {
		for(Object o : content)
			System.out.println(o);
	}

}

 

 

测试代码:

public class MyTableTst {
	private static Shell shell;
	
	public MyTableTst(Shell shell) {
		MyTable table = new MyTable(shell,MyModel.class,Arrays.asList(new String[]{"serialVersionUID","xx_dialog2"}));
	
		/* 
		 * add and remove object
		 */
		Object o = new MyModel(2);
		table.add(o);
		table.add(new MyModel(4));
		table.add(new MyModel(55));
		for(int i=0; i<30; i++)
			table.add(new MyModel(4));
		o = new MyModel(3);
		table.add(o);
		table.remove(o);
		
		/*
		 * set column width and text
		 */
		table.setColumnWidth(300);
//		table.setColumnWidth(new int[]{100,100,150,160,100});
		table.setColumnName(new String[]{"text","id","boolean","b","e"});
		
		/*
		 * set context menu
		 */
		table.setContextMenu(CreateContextMenu(table.getTableViewer()));
		
		/*
		 * reset column label provider
		 */
		for(String property : table.getPropertis()) {
			table.setColumnLabelProvider(property,new ChangedColumnLabelProvider(property));
		}
		table.getTableViewer().refresh();
		
		/*
		 * set sort to the table
		 */
		for(String property : table.getPropertis()) {
			new ColumnViewerSorter(table.getTableViewer(),table.getTableViewerColumn(property),property) {
				protected int doCompare(Object e1, Object e2, String property) {
					if(e1 instanceof MyModel)
						return ((MyModel)e1).doCompare((MyModel)e2, property);
					return 0;
				}
			};
		}
		
		/*
		 * add filter
		 */
		table.getTableViewer().addFilter(new ViewerFilter() {
			public boolean select(Viewer viewer, Object parentElement, Object element) {
				/*
				 * viewer 			- TableViewer
				 * parentElement 	- TableData
				 * element 			- MyModel
				 */
				if(element instanceof MyModel)
					return ((MyModel)element).filter();
				return true;
			}
		});
		
		/*
		 * add EditingSupport
		 */
		TableViewerColumn column = table.getTableViewerColumn("xx_Text_String");
		column.setEditingSupport(new AbstractEditingSupport(table.getTableViewer()) {
			protected Object getValue(Object element) {
				return ((MyModel) element).xx_Text_String;
			}
			protected void doSetValue(Object element, Object value) {
				((MyModel) element).xx_Text_String = value.toString();
			}
		});
	}
	
	private MenuManager CreateContextMenu(TableViewer v) {
		MenuManager menu = new MenuManager();
		menu.add(CeActionFactory.getDelAction(v));
		return menu;
	}

	public static void main(String[] args) {
		Display display = new Display ();
		shell = new Shell(display);
		shell.setLayout(new FillLayout());
		new MyTableTst(shell);
		shell.open ();

		while (!shell.isDisposed ()) {
			if (!display.readAndDispatch ()) display.sleep ();
		}
		display.dispose ();
	}

	protected abstract class AbstractEditingSupport extends EditingSupport {
		private TextCellEditor editor;
		public AbstractEditingSupport(TableViewer viewer) {
			super(viewer);
			this.editor = new TextCellEditor(viewer.getTable());
		}
		protected boolean canEdit(Object element) {
			return true;
		}
		protected CellEditor getCellEditor(Object element) {
			return editor;
		}
		protected void setValue(Object element, Object value) {
			doSetValue(element, value);
			getViewer().update(element, null);
		}
		protected abstract void doSetValue(Object element, Object value);
	}
}

class MyModel {
	protected	int 			xx_Text_int			= 1;
	protected 	long 			longT 				= 1111111111L;
	protected	boolean 		xx_Boolean			= true;
	protected	boolean 		Ignorable_Boolean	= true;
	public 		String 			xx_Text_String		= "a string";
	protected 	List<String> 	list_dialog1 		= Arrays.asList(new String[]{"list1","list2"}); //端口或者引脚 Clock sources ports or pins
	protected 	String 			xx_dialog2 			= "dialog2"; 
	protected 	String 			xx_Combo_list1 		= ""; 

	public MyModel() {}
	public MyModel(int i) {
		xx_Text_int = i;
	}
	
	/*
	 * false - filter.
	 * true  - display.
	 */
	public boolean filter() {
		if(xx_Text_int == 5)
			return false;
		return true;
	}

	public int doCompare(MyModel model, String field) {
		if(field.equals("xx_Text_int"))
			return ((Integer)this.xx_Text_int).compareTo((Integer)model.xx_Text_int);
		if(field.equals("longT"))
			return ((Long)this.longT).compareTo((Long)model.longT);
		if(field.equals("xx_Boolean"))
			return ((Boolean)this.xx_Boolean).compareTo((Boolean)model.xx_Boolean);
		if(field.equals("Ignorable_Boolean"))
			return ((Boolean)this.Ignorable_Boolean).compareTo((Boolean)model.Ignorable_Boolean);
		if(field.equals("xx_Text_String"))
			return this.xx_Text_String.compareTo(model.xx_Text_String);
		if(field.equals("list_dialog1"))
			return ((Integer)this.list_dialog1.size()).compareTo((Integer)model.list_dialog1.size());
		if(field.equals("xx_dialog2"))
			return this.xx_dialog2.compareTo(model.xx_dialog2);
		if(field.equals("xx_Combo_list1"))
			return this.xx_Combo_list1.compareTo(model.xx_Combo_list1);
		return 0;
	}
}

class ChangedColumnLabelProvider extends ColumnLabelProvider {
	private String columnText;

	public ChangedColumnLabelProvider(String columnText) {
		super();
		this.columnText = columnText;
	}

	public Image getImage(Object element) {
		return Display.getCurrent().getSystemImage(SWT.ICON_WARNING);
	}

	public Font getFont(Object element) {
		return JFaceResources.getFont(JFaceResources.HEADER_FONT);
	}

	public Color getBackground(Object element) {
		return Display.getCurrent().getSystemColor(SWT.COLOR_GRAY);
	}

	public Color getForeground(Object element) {
		return Display.getCurrent().getSystemColor(SWT.COLOR_GREEN);
	}

	public String getText(Object element) {
		Object o = getClassFieldContent(element, columnText);
		return o == null ?"":o.toString();
	}

	private Object getClassFieldContent(Object obj, String fieldName) {
		Object o = null;
		for(Field f : obj.getClass().getDeclaredFields()) {
			if(f.getName().equals(fieldName)) {
				f.setAccessible(true);
				try {
					o = f.get(obj);
				} catch (IllegalArgumentException e) {
					e.printStackTrace();
				} catch (IllegalAccessException e) {
					e.printStackTrace();
				}
			}
		}
		return o;
	}

	public void dispose(ColumnViewer viewer, ViewerColumn column) {
		super.dispose(viewer, column);
	}
}

class CeActionFactory {
	public static Action getDelAction(final TableViewer v) {
		Action action = new Action("Del") {
			public void run() {
				v.getTable().remove(v.getTable().getSelectionIndices());
			}
		};
		action.setImageDescriptor(ImageDescriptor.createFromImage(
				Display.getCurrent().getSystemImage(SWT.ICON_ERROR)));
		return action;
	}
}

 

 

测试了功能:

a)可设置列的默认宽,可设置每一列的宽。可改变列的名字。
b)可设置Table上下文的菜单。
c)可以添加,删除,删除所有。
d)可以接受更改columnLabelProvide。
e)编辑,是不是用editorsupport更方便,看看。
f)Sort扩展。
g)Filter。

 

分享到:
评论

相关推荐

    具有特效通用表格样式

    "具有特效通用表格样式"的主题聚焦于如何创建和定制灵活且美观的表格,使得数据的展示更加直观易读。下面将详细讨论相关知识点。 首先,我们来看“通用表格样式”。这意味着这些样式设计适用于各种场景,无论是在...

    表格模板-通用表格.xlsx

    表格模板-通用表格.xlsx

    C#通用表格打印

    本主题聚焦于“C#通用表格打印”,这是一个针对初学者非常实用的技术点,旨在帮助开发者实现打印各种类型的报表功能。下面我们将深入探讨这个知识点。 首先,要实现C#中的表格打印,我们需要理解.NET Framework提供...

    测量通用表格(种类多,非常丰富)

    在IT行业中,尤其是在数据分析、项目管理和工程领域,通用表格的使用是至关重要的。"测量通用表格(种类多,非常丰富)"这个资源集合提供了一系列适用于各种测量任务的表格,旨在帮助用户快速有效地进行数据记录和...

    Excel坐标展点CAD通用表格.xls

    Excel坐标展点CAD通用表格

    江苏水利工程通用表格(规范).doc

    文档“江苏水利工程通用表格(规范).doc”是一个包含江苏水利工程中各参与方使用的标准化表格集。这些表格主要用于规范施工过程中的各个关键环节,确保工程的质量、进度和费用控制。以下是根据表格标题和描述概括出的...

    成本控制通用表格.doc

    文档中的内容主要涉及的是工程项目的成本控制和管理,包括了多个关键表格,用于跟踪和管理工程的成本、分包情况、物资使用以及财务费用等。以下是这些知识点的详细说明: 1. **成本控制表格**:成本控制是工程项目...

    SysListView32通用表格控件内容读取程序

    刚刚写的用来读取Windows通用控件之表格控件的程序. 在这两天学习Windows的服务的时候觉得要把MMC中服务管理列表提取出来研究所以做了这个软件,拿出来给大家共享 。主要用到的是: WriteProcessMemory ...

    5210预收款项通用表格.zip

    这个"5210预收款项通用表格.zip"压缩包显然包含了与预收款项管理相关的资料,其中的核心文件是"5210预收款项通用表格.xls",这应该是一个Excel电子表格,用于记录和追踪企业的预收款项情况。 预收款项,顾名思义,...

    手机钢化膜通用表格202008版本

    手机钢化膜通用表格202008版本,手机钢化膜通用表格202008版本。目前最新的版本,可以直接代用。

    表格模板-通用表格1.xlsx

    表格模板-通用表格1.xlsx

    5160应付票据通用表格.zip

    标题中的“5160应付票据通用表格”指的是企业财务管理中的一种常见表格,主要用于记录和管理企业的应付票据信息。在企业会计系统中,应付票据是企业对外部债权人承诺在未来特定日期支付的一种短期债务,通常包括商业...

    5420应付权证通用表格.zip

    标题中的“5420应付权证通用表格.zip”表明这是一个关于应付权证的文档集合,通常用于财务管理和会计操作。应付权证是企业发行的一种金融工具,它给予持有者在特定日期或之前以特定价格购买公司股票的权利,是企业...

    获奖名单通用表格excel模版下载.xlsx

    获奖名单通用表格excel模版下载.xlsx

    管道工程竣工资料表格通用表格.doc

    管道工程竣工资料表格通用表格.doc

    表格模板-通用空白表格模板.xlsx

    表格模板-通用空白表格模板.xlsx

    5400应付利息通用表格.zip

    【5400应付利息通用表格】是一个与财务管理和会计工作相关的资料压缩包,其中包含了一个名为"5400应付利息通用表格.xls"的Excel文件。在企业财务管理中,"应付利息"是一项重要的财务指标,它反映了企业在一定期间内...

Global site tag (gtag.js) - Google Analytics