스파크라인 셰이프

자동 셰이프와 그림 셰이프는 이제 스파크라인 렌더링을 지원하며, 스파크라인은 셰이프를 통해 이동, 크기 조정, 회전이 가능합니다.

자동 셰이프와 그림 셰이프가 이제 스파크라인 렌더링을 지원합니다. 다음 예시는 그림 셰이프에 스파크라인을 설정하는 방법을 보여줍니다. 다음 예시는 자동 셰이프에 스파크라인을 설정하는 방법을 보여줍니다.
<template> <div class="sample-tutorial"> <gc-spread-sheets class="sample-spreadsheets" @workbookInitialized="initSpread"> <gc-worksheet></gc-worksheet> </gc-spread-sheets> </div> </template> <script> import Vue from "vue"; import "@mescius/spread-sheets-vue"; import "@mescius/spread-sheets-shapes"; import GC from "@mescius/spread-sheets"; import '@mescius/spread-sheets-resources-ko'; GC.Spread.Common.CultureManager.culture("ko-kr"); let App = Vue.extend({ name: "app", data: function () { return { spread: null }; }, methods: { initSpread(spread) { spread.addSparklineEx(new Clock()); var sheet = spread.getActiveSheet(); initGaugeSparklineSample(sheet); initColumnSparklineSample(sheet); initCustomSparklineSample(sheet); } } }); function initGaugeSparklineSample(sheet) { sheet.setValue(12, 1, 10000); var shape = sheet.shapes.add('', GC.Spread.Sheets.Shapes.AutoShapeType.roundedRectangularCallout, 68, 30, 235, 200); var style = shape.style(); style.fill = { src: '' }; style.line.width = 2; style.line.color = 'rgb(0,0,0)'; shape.style(style); shape.adjustments([-0.317, 0.545, 0.16667]); shape.setFormula('style.fill.src', '=GAUGEKPISPARKLINE(28000,Sheet1!B13,0,50000,TRUE,TEXT(28000,"$0,K"),TEXT(Sheet1!B13,"$0,K"),TEXT(0,"$0,K"),TEXT(50000,"$0,K"),,-90,90,0.5,0,{0,10000,"#F7A711"},{10000,25000,"#BBBBBB"},{25000,50000,"#82BC00"})'); var spinButton = addSpinButton(sheet, 260, 62, 38, 58, '=Sheet1!B13', 0, 50000, 1000, 10000); sheet.shapes.group([shape, spinButton]); } function initColumnSparklineSample(sheet) { sheet.getRange(12, 6, 1, 5).hAlign(1); var shape = sheet.shapes.addPictureShape('', '', 378, 30, 296, 205); var spin1 = addSpinButton(sheet, 396, 188, 28, 38, '=Sheet1!G13', 0, 10, 1, 5); var spin2 = addSpinButton(sheet, 454, 188, 28, 38, '=Sheet1!H13', 0, 10, 1, 3); var spin3 = addSpinButton(sheet, 512, 188, 28, 38, '=Sheet1!I13', 0, 10, 1, 2); var spin4 = addSpinButton(sheet, 570, 188, 28, 38, '=Sheet1!J13', 0, 10, 1, 4); var spin5 = addSpinButton(sheet, 628, 188, 28, 38, '=Sheet1!K13', 0, 10, 1, 1); var style = shape.style(); style.fill = { type: GC.Spread.Sheets.Shapes.GradientFillType.linear, angle: 90, stops: [ { position: 0, color: '#B993D6' }, { position: 1, color: '#8CA6DB' } ] }; style.line.width = 2; style.line.color = 'rgb(0,0,0)'; shape.style(style); let pictureFormat = shape.pictureFormat(); pictureFormat.crop = { left: 0, right: 0, top: -0.05, bottom: -0.35 }; shape.pictureFormat(pictureFormat); shape.geometryType(GC.Spread.Sheets.Shapes.AutoShapeType.roundedRectangle); shape.setFormula('src', '=COLUMNSPARKLINE(Sheet1!G13:K13,1)'); sheet.shapes.group([shape, spin1, spin2, spin3, spin4, spin5]); } function initCustomSparklineSample (sheet) { sheet.getRange(21, 1, 1, 3).hAlign(0).vAlign(1); sheet.setRowHeight(21, 40); addSpinButton(sheet, 94, 420, 30, 40, 'Sheet1!B22', 0, 23, 1, 12); addSpinButton(sheet, 156, 420, 30, 40, 'Sheet1!C22', 0, 59, 1, 45); addSpinButton(sheet, 218, 420, 30, 40, 'Sheet1!D22', 0, 59, 1, 30); var shape = sheet.shapes.addPictureShape('', '', 70, 265, 150, 150); shape.setFormula('src', '=CUSTOMECLOCKSPARKLINE(Sheet1!B22,Sheet1!C22,Sheet1!D22)'); } function addSpinButton (sheet, x, y, width, height, cellLink, minValue, maxValue, step, value) { var spinButton = sheet.shapes.addFormControl('', GC.Spread.Sheets.Shapes.FormControlType.spinButton, x, y, width, height); var options = spinButton.options(); options.cellLink = cellLink; options.minValue = minValue; options.maxValue = maxValue; options.step = step; spinButton.options(options); spinButton.value(value); return spinButton; } class Clock extends GC.Spread.Sheets.Sparklines.SparklineEx { createFunction () { var func = new GC.Spread.CalcEngine.Functions.Function("CUSTOMECLOCKSPARKLINE", 3, 3); func.evaluate = function (args) { return { hours: args[0], mintues: args[1], seconds: args[2] }; }; return func; } paint (context, value, x, y, width, height) { var centerX = x + width / 2; var centerY = y + height / 2; var margin = 10; var padding = 10; var radius = Math.min(width, height) / 2 - margin; if (!value || radius <= 0) { return; } context.save(); //draw circle this._drawCircle(context, centerX, centerY, radius); //draw center this._drawCenter(context, centerX, centerY, 3); //draw hands this._drawHands(context, value, centerX, centerY, radius); //draw numerals this._drawNumerals(context, centerX, centerY, radius - padding); context.restore(); } _drawNumerals (context, centerX, centerY, radius) { var numerals = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]; context.textAlign = "right"; context.font = "12px sans-serif"; numerals.forEach(function (numeral) { var angle = Math.PI / 6 * (numeral - 3); var numeralWidth = context.measureText(numeral).width; context.beginPath(); context.fillText(numeral, centerX + Math.cos(angle) * radius + numeralWidth / 2, centerY + Math.sin(angle) * radius + numeralWidth / 2); }); } _drawHands (context, value, centerX, centerY, radius) { var hours = value.hours, mintues = value.mintues, seconds = value.seconds; hours = hours > 12 ? hours - 12 : hours; this._drawHand(context, centerX, centerY, hours * 5 + (mintues / 60) * 5, radius / 2); this._drawHand(context, centerX, centerY, mintues, radius * 3 / 4); context.strokeStyle = "red"; this._drawHand(context, centerX, centerY, seconds, radius * 3 / 4); } _drawHand (context, centerX, centerY, loc, radius) { var angle = (Math.PI * 2) * (loc / 60) - Math.PI / 2; context.beginPath(); context.moveTo(centerX, centerY); context.lineTo(centerX + Math.cos(angle) * radius, centerY + Math.sin(angle) * radius); context.stroke(); }; _drawCenter (context, centerX, centerY, radius) { context.beginPath(); context.arc(centerX, centerY, radius, 0, Math.PI * 2, true); context.fill(); } _drawCircle (context, centerX, centerY, radius) { context.beginPath(); context.arc(centerX, centerY, radius, 0, Math.PI * 2, true); context.stroke(); }; } new Vue({ render: h => h(App) }).$mount("#app"); </script> <style scoped> .sample-tutorial { position: relative; height: 100%; overflow: hidden; } .sample-spreadsheets { width: 100%; height: 100%; overflow: hidden; float: left; } body { position: absolute; top: 0; bottom: 0; left: 0; right: 0; } </style>
<!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"> <!-- SystemJS --> <script src="$DEMOROOT$/ko/vue/node_modules/systemjs/dist/system.src.js"></script> <script src="systemjs.config.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>
(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-vue': 'npm:@mescius/spread-sheets-vue/index.js', '@mescius/spread-sheets-shapes': 'npm:@mescius/spread-sheets-shapes/index.js', '@mescius/spread-sheets-resources-ko': 'npm:@mescius/spread-sheets-resources-ko/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);