레이아웃 모드
TableSheet는 groupLayout에 의해 설정할 수 있는 세 가지 다른 그룹 레이아웃을 지원합니다.
그룹 레이아웃 모드:
표
개요
압축
그룹 필드
사용자는 여러 그룹 필드를 동시에 또는 각 필드별로 설정할 수 있습니다.
간격
고객은 간격을 표시하여 루트 그룹 수준 항목을 간격으로 구분할 수 있습니다.
간격은 Outline 및 Condensed 모드에서만 사용할 수 있습니다.
여러 그룹 필드
그룹화된 항목의 콘텐츠에 대해 서로 다른 수준의 들여쓰기를 사용하여 다수의 그룹 제목을 추가할 수 있습니다.
요약 필드 옵션
사용자는 각 필드의 콘텐츠를 설정할 수 있습니다.
<template>
<div id="split-view" class="sample-tutorial">
<gc-spread-sheets
class="sample-spreadsheets split-content"
@workbookInitialized="initSpread"
>
</gc-spread-sheets>
<div class="split-panel">
<div class="split-tabs">
<button
class="split-tab-link"
:class="{ active: selectedTab === 0 }"
@click="selectTab(0)"
>
TableSheet Panel
</button>
<button
class="split-tab-link"
:class="{ active: selectedTab === 1 }"
@click="selectTab(1)"
>
Setting
</button>
</div>
<div class="split-panels">
<div
id="panel"
class="split-tab-content container"
:key="0"
v-show="selectedTab === 0"
></div>
<div
id="settings"
class="split-tab-content options-container"
:key="1"
v-show="selectedTab === 1"
>
<fieldset>
<legend>Group Layout Mode</legend>
<select v-model.number="tableSheetGroupLayoutMode">
<option :value="0">Tabular</option>
<option :value="1">Outline</option>
<option :value="2">Condensed</option>
</select>
</fieldset>
<fieldset>
<legend>Default Summary Position</legend>
<select v-model.number="tableSheetGroupLayoutPosition">
<option value="header" selected>Header</option>
<option value="footer">Footer</option>
</select>
</fieldset>
</div>
</div>
</div>
</div>
</template>
<script>
import Vue from "vue";
import "@mescius/spread-sheets-vue";
import GC from "@mescius/spread-sheets";
import "@mescius/spread-sheets-tablesheet";
import '@mescius/spread-sheets-resources-ko';
GC.Spread.Common.CultureManager.culture("ko-kr");
import "./styles.css";
let App = Vue.extend({
name: "app",
sheet: null,
data() {
return {
selectedTab: 0,
tableSheetGroupLayoutMode: 1,
tableSheetGroupLayoutPosition: "header",
OutlineAndCondensedGroup: [
{
field: "Office",
caption: "OFFICE",
style: { foreColor: '#000000', backColor: '#ededed', fontSize: "20px", cellPadding: "16 0 0 0" },
headerStyle: { font: "10px Arial", foreColor: "#666", cellPadding: "2 0 0 0" },
summaryFields: [
{
caption: "COUNT",
formula: "=COUNTA([OrderID])",
style: { foreColor: "rgb(185, 122, 87)", fontSize: "20px", cellPadding: "16 0 0 0" },
headerStyle: { font: "10px Arial", foreColor: "#666", cellPadding: "2 0 0 0" }
},
{
caption: "TOTAL AMOUNT",
formula: '=SUM([Amount])',
relateTo: "Amount",
style: { formatter: "$ #,##0.00", cellPadding: "30 0 0 0" },
headerStyle: { cellPadding: "8 0 0 0" }
},
{
caption: "Σ(Quantity)",
formula: "=SUM([Quantity])",
style: { cellPadding: "30 0 0 0" },
headerStyle: { cellPadding: "8 0 0 0" }
},
]
},
{
field: "OrderDate",
spacing: { row: 20 },
caption: "ORDER DATE",
style: { foreColor: '#000000', backColor: '#f7f7f7', fontSize: "20px", cellPadding: "16 0 0 0" },
headerStyle: { font: "10px Arial", foreColor: "#666", cellPadding: "2 0 0 0" },
summaryFields: [
{
caption: "SUBTOTAL AMOUNT",
formula: '=SUM([Amount])',
position: "footer",
relateTo: "Amount",
style: { formatter: "$ #,##0.00", cellPadding: "30 0 0 0" },
headerStyle: { cellPadding: "8 0 0 0" }
},
{
caption: "SUBTOTAL COUNT",
formula: "=SUM([Quantity])",
position: "footer",
style: { cellPadding: "30 0 0 0" },
headerStyle: { cellPadding: "8 0 0 0" }
}
]
}
],
TabularGroup: [
{
field: "Office",
caption: "OFFICE",
style: { foreColor: '#000000', backColor: '#ededed', fontSize: "20px" },
headerStyle: { font: "10px Arial", foreColor: "#666" },
summaryFields: [
{
caption: "COUNT",
formula: "=COUNTA([OrderID])",
style: { foreColor: "rgb(185, 122, 87)", fontSize: "20px" },
headerStyle: { font: "10px Arial", foreColor: "#666" }
},
{
caption: "TOTAL AMOUNT",
formula: '=SUM([Amount])',
relateTo: "Amount",
style: { formatter: "$ #,##0.00" },
},
{
caption: "Σ(Quantity)",
formula: "=SUM([Quantity])",
},
]
},
{
field: "OrderDate",
spacing: { row: 20 },
caption: "ORDER DATE",
style: { foreColor: '#000000', backColor: '#f7f7f7', fontSize: "20px" },
headerStyle: { font: "10px Arial", foreColor: "#666" },
summaryFields: [
{
caption: "SUBTOTAL AMOUNT",
formula: '=SUM([Amount])',
position: "footer",
relateTo: "Amount",
style: { formatter: "$ #,##0.00" },
},
{
caption: "SUBTOTAL COUNT",
formula: "=SUM([Quantity])",
position: "footer",
}
]
}
]
};
},
watch: {
tableSheetGroupLayoutMode(newVal, oldVal) {
this.resetGroupLayout();
},
tableSheetGroupLayoutPosition(newVal, oldVal) {
this.resetGroupLayout();
}
},
methods: {
initSpread: function (spread) {
spread.suspendPaint();
spread.options.autoFitType = GC.Spread.Sheets.AutoFitType.cellWithHeader;
spread.options.scrollByPixel = true;
spread.options.scrollPixel = 5;
var self = this;
//init a data manager
var dataManager = spread.dataManager();
var ordersTable = dataManager.addTable("ordersTable", {
data: orderDataSource,
schema: {
type: "csv",
columns: {
OrderDate: { dataType: "date" },
ShipDate: { dataType: "date" },
Quantity: { dataType: "number" },
Amount: { dataType: "number" },
},
},
});
//init a table sheet
var sheet = spread.addSheetTab(
0,
"TableSheet1",
GC.Spread.Sheets.SheetType.tableSheet
);
self.sheet = sheet;
sheet.setDefaultRowHeight(40, GC.Spread.Sheets.SheetArea.colHeader);
sheet.options.allowAddNew = false; //hide new row
sheet.options.groupLayout.mode = GC.Spread.Sheets.TableSheet.GroupLayoutMode.outline; // apply the outline group layout mode
sheet.options.showRowNumber = true;
sheet.applyTableTheme(GC.Spread.Sheets.Tables.TableThemes.light1);
sheet.options.alternatingRowOptions = {
step: [1, 1],
style: new GC.Spread.Sheets.Style("#ffffff"),
};
//bind a view to the table sheet
ordersTable.fetch().then(function () {
var myView = ordersTable.addView("myView", [
{ value: "OrderID", width: 180, style: { formatter: "O00000" } },
{ value: "Product", width: 200 },
{ value: "Quantity", width: 100 },
{ value: "OrderDate", width: 100, visible: false },
{ value: "ShipDate", width: 100, visible: false },
{ value: "Office", width: 100 },
{ value: "Category", width: 150 },
{ value: "Amount", width: 120 },
]);
sheet.setDataView(myView);
//init a table sheet panel
var host = document.getElementById("panel");
var panel = new GC.Spread.Sheets.TableSheet.TableSheetPanel(
"myPanel",
sheet,
host
);
sheet.groupBy(self.OutlineAndCondensedGroup);
});
spread.resumePaint();
initSplitView(spread);
},
resetGroupLayout: function () {
this.sheet.options.groupLayout = {
mode: this.tableSheetGroupLayoutMode,
position: this.tableSheetGroupLayoutPosition
};
if (this.tableSheetGroupLayoutMode === 0) {
this.sheet.groupBy(this.TabularGroup);
} else {
this.sheet.groupBy(this.OutlineAndCondensedGroup);
}
},
selectTab(index) {
this.selectedTab = index;
},
},
});
function initSplitView(spread) {
var host = document.getElementById("split-view");
var content = host.getElementsByClassName("split-content")[0];
var panel = host.getElementsByClassName("split-panel")[0];
new SplitView({
host: host,
content: content,
panel: panel,
refreshContent: function () {
spread.refresh();
},
defaultPanelWidth: 320,
allowResize: false,
});
}
new Vue({
render: (h) => h(App),
}).$mount("#app");
</script>
<!doctype html>
<html style="height:100%;font-size:14px;">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link rel="stylesheet" type="text/css" href="$DEMOROOT$/ko/vue/node_modules/@mescius/spread-sheets/styles/gc.spread.sheets.excel2013white.css">
<link rel="stylesheet" type="text/css" href="$DEMOROOT$/spread/source/splitView/splitView.css">
<!-- SystemJS -->
<script src="$DEMOROOT$/ko/vue/node_modules/systemjs/dist/system.src.js"></script>
<script src="$DEMOROOT$/spread/source/data/orderDataSource.js" type="text/javascript"></script>
<script src="systemjs.config.js"></script>
<!-- plugins -->
<script src="$DEMOROOT$/spread/source/splitView/SplitView.js"></script>
<script>
System.import('./src/app.vue');
System.import('$DEMOROOT$/ko/lib/vue/license.js');
</script>
</head>
<body>
<div id="app"></div>
</body>
</html>
.sample-tutorial {
position: relative;
height: 100%;
overflow: hidden;
}
body {
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
margin: 0;
}
.sample-spreadsheets {
width: calc(100% - 303px);
height: 100%;
overflow: hidden;
float: left;
}
.container {
width: 300px;
height: 100%;
float: left;
border: 1px solid lightgrey;
}
fieldset select {
margin-top: 6px;
padding: 4px 6px;
width: 125px;
}
fieldset input {
margin-top: 6px;
padding: 4px 6px;
width: 110px;
}
.split-panels {
height: 535px;
}
.tab-container {
width: 50%;
margin: 0 auto;
}
.split-tabs {
position: absolute;
top: 12px;
right: 5px;
display: flex;
justify-content: flex-start;
flex-direction: row;
align-items: center;
}
.split-tab-link {
height: 30px;
background-color: #f1f1f1;
border: none;
cursor: pointer;
transition: background-color 0.3s;
margin-bottom: 10px;
}
.split-tab-link:hover {
background-color: #ddd;
}
.split-tab-link.active {
background-color: #ccc;
}
.split-tab-content.active {
display: block;
}
(function (global) {
System.config({
transpiler: 'plugin-babel',
babelOptions: {
es2015: true
},
meta: {
'*.css': { loader: 'css' },
'*.vue': { loader: 'vue-loader' }
},
paths: {
// paths serve as alias
'npm:': 'node_modules/'
},
// map tells the System loader where to look for things
map: {
'@mescius/spread-sheets': 'npm:@mescius/spread-sheets/index.js',
'@mescius/spread-sheets-tablesheet': 'npm:@mescius/spread-sheets-tablesheet/index.js',
'@mescius/spread-sheets-resources-ko': 'npm:@mescius/spread-sheets-resources-ko/index.js',
'@mescius/spread-sheets-vue': 'npm:@mescius/spread-sheets-vue/index.js',
'@grapecity/jsob-test-dependency-package/react-components': 'npm:@grapecity/jsob-test-dependency-package/react-components/index.js',
'jszip': 'npm:jszip/dist/jszip.js',
'css': 'npm:systemjs-plugin-css/css.js',
'vue': 'npm:vue/dist/vue.min.js',
'vue-loader': 'npm:systemjs-vue-browser/index.js',
'tiny-emitter': 'npm:tiny-emitter/index.js',
'plugin-babel': 'npm:systemjs-plugin-babel/plugin-babel.js',
'systemjs-babel-build':'npm:systemjs-plugin-babel/systemjs-babel-browser.js'
},
// packages tells the System loader how to load when no filename and/or no extension
packages: {
src: {
defaultExtension: 'js'
},
rxjs: {
defaultExtension: 'js'
},
"node_modules": {
defaultExtension: 'js'
}
}
});
})(this);