/* function chartSkeleton(nr, title, subtitle, dimension1Fldname, dimension1Caption, hasDimension2, dimension2Fldname, dimension2Caption, measure1Fldname, measure1Caption, hasMeasure2, measure2Fldname, measure2Caption ) { this.nr=nr; this.title=title; this.subtitle=subtitle; this.dimension1Fldname=dimension1Fldname; this.dimension1Caption=dimension1Caption; this.dimension2Fldname=dimension2Fldname; this.dimension2Caption=dimension2Caption; this.measure1Fldname=measure1Fldname; this.measure1Caption=measure1Caption; this.measure2Fldname=measure2Fldname; this.measure2Caption=measure2Caption; this.hasDimension2 = function () { if(dimension2Fldname && dimension2Fldname !="") return true; else return false; } }*/ function d3dataRow(nr,dimension1,dimension2,measure1 ) { this.nr=nr; this.dimension1=dimension1; this.dimension2=dimension2; this.measure1=measure1; } function commonChartProperty(name, caption, isMandatory, inputType, staticValues, range_from, range_to, defaultValue, propUnit, explanation, groupCaption, groupUniquename, rendererUniquename, groupVariableName, variableName, propValueType, isGeneric ) { this.name=name; this.caption=caption; this.staticValues=staticValues; this.range_from=range_from; this.range_to=range_from; this.isMandatory=isMandatory; this.inputType=inputType; this.defaultValue=defaultValue; this.propUnit=propUnit; this.explanation=explanation; this.groupCaption=groupCaption; this.groupUniquename=groupUniquename; this.rendererUniquename=rendererUniquename; this.groupVariableName=groupVariableName; this.variableName=variableName; this.propValueType=propValueType; this.isGeneric=isGeneric; this.getValueResultset = function () { var valueOptions=[]; var optionCounter=0; var staticValueArray = staticValues.split(/\|/); for(var j=0;j < staticValueArray.length;j++) { var isDefault=false; if(staticValueArray[j]) { if(staticValueArray[j]==this.defaultValue) isDefault=true; var o=new selectionPropertyValue(optionCounter,staticValueArray[j],staticValueArray[j],isDefault); valueOptions[optionCounter]=o; optionCounter++; } } return valueOptions; } } function commonChartPropertyGroup(caption,groupUniquename,groupVariableName) { this.caption=caption; this.groupUniquename=groupUniquename; this.groupVariableName=groupVariableName; } function renderEChart(chartCode,chartDiv,ergebniselementOrdnr) { /*obsolete*/ // Initialize the echarts instance based on the prepared dom var myChart = echarts.init(document.getElementById(chartDiv),null, { renderer: 'svg' }); var datasetSourceRow=new Array(); var datasetSourceCol=new Array(); //first header row: var columnCount=rsColumnMetaData[ergebniselementOrdnr].length; var rowCount=rs[ergebniselementOrdnr].length; datasetSourceCol=['Fakultät (Schlüssel)','Fakultät','Anzahl der Studierenden','Anteil der Studierenden (in %)']; datasetSourceRow.push(datasetSourceCol); //now the data: for(var i=0;i < rowCount;i++) { var datasetSourceCol=new Array(); datasetSourceCol.push(rs[ergebniselementOrdnr][i].dim_studiengang_fb); datasetSourceCol.push(rs[ergebniselementOrdnr][i].dim_studiengang_fb_str); datasetSourceCol.push(rs[ergebniselementOrdnr][i].summe); datasetSourceCol.push(rs[ergebniselementOrdnr][i].anteil); datasetSourceRow.push(datasetSourceCol); } // Specify the configuration items and data for the chart var datasetObj={dataset: { source: datasetSourceRow } }; //var chartCodeObj = JSON.parse(chartCode); let optionsObj = { ...datasetObj, ...chartCode }; // Display the chart using the configuration items and data just specified. myChart.setOption(optionsObj); } function openModalCardDetail(ergebniselementOrdnr) { var myModalCard=document.getElementById("modalCardDetail"+ergebniselementOrdnr); myModalCard.classList.add('is-active'); renderEChart("modalCardDetailImage"+ergebniselementOrdnr,ergebniselementOrdnr); } function fillEchartsDataSet(myRs,myRsMetaData,currentChartModel) { var dataset =new Array(); var chartType=currentChartModel.chartElements[0].vizTypeUniquename; //Identify dimensions and measures: switch (chartType) { case "echarts_pie": var measure1Fldname=getChartElementPropertyValueFromModel(currentChartModel,"1","measure1"); var dimension1Fldname=getChartElementPropertyValueFromModel(currentChartModel,"1","dimension1"); dataset=fillEchartsDataSetNameValue(myRs,myRsMetaData,dimension1Fldname,measure1Fldname); break; case "echarts_bar_y_stack": //TODO klappt nich tnicht) var measure1Fldname=getChartElementPropertyValueFromModel(currentChartModel,"1","measure1"); var dimension1Fldname=getChartElementPropertyValueFromModel(currentChartModel,"1","dimension1"); var dimension2Fldname=getChartElementPropertyValueFromModel(currentChartModel,"1","dimension2"); dataset=fillEchartsDataSetCrosstab(myRs,myRsMetaData,dimension1Fldname,dimension2Fldname,measure1Fldname); break; default: dataset=fillEchartsDataSetSimpleCopy(myRs,myRsMetaData); break; } return dataset; } function fillEchartsDataSetSimpleCopy(myRs,myRsMetaData) { var myDimensions=[]; var mySource=[]; myRsMetaData.forEach((row) => { for (var col in row) { console.log(col +"-"+row[col]); if(col=="colname" && row[col]) { myDimensions.push(row[col]); } } }); var rowcount=myRs.length; var rownr=1; console.log("Zeilenanzahl " +rowcount); myRs.forEach((row) => { mySource.push(row); rownr++; } ); //TODO:Sorting and filtering return {dimensions:myDimensions, source: mySource }; } function fillEchartsDataSetCrosstab(myRs,myRsMetaData,dimension1Fldname,dimension2Fldname,measure1Fldname) { //TODO, klappt noch nicht var datasetSourceRow=new Array(); var datasetSourceCol=new Array(); var columnCount=myRsMetaData.length; var rowCount=myRs.length; //zuerst die Überschrift: //erste Spalte enthält Dimension 1, die weiteren Spalten dann die Ausprägungen von Dimension 2: var dimension1Value; var dimension2Value; var previousDimension1Value=""; var previousDimension2Value=""; var measure1Value; var isFirstTargetRow=true; myRs.forEach((row) => { for (var col in row) { //console.log(col +"-"+row[col]); if(col==dimension1Fldname) dimension1Value=row[col]; if(col==dimension2Fldname) dimension2Value=row[col]; if(col==measure1Fldname) measure1Value=row[col]; if(dimension1Value!=previousDimension1Value) { var datasetSourceRow=new Array(); var datasetSourceCol=new Array(); datasetSourceCol.push(dimension1Value); if(dimension2Value!=previousDimension2Value) datasetSourceCol.push(dimension2Value); } var datasetSourceCol=new Array(); datasetSourceCol.push(dimension1Value); datasetSourceCol.push(measure1Value); datasetSourceRow.push(datasetSourceCol); } }); //datasetSourceCol=[dimension1Fldname,dimension2Fldname,measure1Fldname]; //datasetSourceRow.push(datasetSourceCol); //now the data: //bei pie chartdimensions:myDimensionss ist die erste Spalte der Name, die zweite der Wert: /* for(var i=0;i < rowCount;i++) { var datasetSourceCol=new Array(); datasetSourceCol.push(myRs[i].dim_studiengang_fb); datasetSourceCol.push(myRs[i].summe); datasetSourceRow.push(datasetSourceCol); }*/ return datasetSourceRow; } function fillEchartsDataSetNameValue(myRs,myRsMetaData,dimension1Fldname,measure1Fldname) { var datasetSourceRow=new Array(); var datasetSourceCol=new Array(); var columnCount=myRsMetaData.length; var rowCount=myRs.length; datasetSourceCol=[dimension1Fldname,measure1Fldname]; datasetSourceRow.push(datasetSourceCol); //now the data: //bei pie chartdimensions:myDimensionss ist die erste Spalte der Name, die zweite der Wert: var dimension1Value; var measure1Value; myRs.forEach((row) => { for (var col in row) { //console.log(col +"-"+row[col]); if(col==dimension1Fldname) dimension1Value=row[col]; if(col==measure1Fldname) measure1Value=row[col]; } var datasetSourceCol=new Array(); datasetSourceCol.push(dimension1Value); datasetSourceCol.push(measure1Value); datasetSourceRow.push(datasetSourceCol); }); /* for(var i=0;i < rowCount;i++) { var datasetSourceCol=new Array(); datasetSourceCol.push(myRs[i].dim_studiengang_fb); datasetSourceCol.push(myRs[i].summe); datasetSourceRow.push(datasetSourceCol); }*/ return datasetSourceRow; } /* plot and d3 start:*/ function renderPlotD3Chart(chartDiv,currentChartModel,ergebniselementOrdnr) { /*if(document.getElementById("chartName").value=="") document.getElementById("chartName").value=vizInitialName;*/ if(currentChartModel.chartElements.length>0 && currentChartModel.chartElements[0]) { renderChartSVGFromModel(currentChartModel,chartDiv,ergebniselementOrdnr); } else document.getElementById(chartDiv).innerHTML=""+ ""; // } /* Render Model:*/ function renderChartSVGFromModel(currentChartModel,targetDiv,ergebniselementOrdnr,title) { //first update data if function is defined: if(currentChartModel.dataTransformation.length>0) { for(var k=0;k< currentChartModel.dataTransformation.length;k++) { var myFunc=currentChartModel.dataTransformation[k]; for(var row=0;row < rs[ergebniselementOrdnr].length;row++) { rs[ergebniselementOrdnr][row][myFunc.colname]=applyFunction(rs[ergebniselementOrdnr][row][myFunc.colname],myFunc.colfunction); } } } switch (currentChartModel.renderer) { case "plot": renderChartSVGfromModelWithPlot(currentChartModel,targetDiv,ergebniselementOrdnr); break; case "d3js": renderChartSVGWithD3(currentChartModel,targetDiv,ergebniselementOrdnr); break; case "echarts": renderEChart2(currentChartModel,targetDiv,ergebniselementOrdnr,title); break; default: alert("No renderer"); break; } return true; } function renderChartSVGfromModelWithPlot (currentChartModel,targetDiv,ergebniselementOrdnr) { console.log("using Plot"); var myOptions=new Object; //myOptions.marks=new Array(); //myOptions.sort=new Array(); myOptions=getPlotOptionsObj(currentChartModel.chartPropertiesUsed,currentChartModel); var marksArray=new Array(); /*for(var k=0;k< myChartModel.chartPropertiesUsed.length;k++) { }*/ //first empty marks: for(var k=0;k< myOptions["marks"].length;k++) { myOptions["marks"][k].pop(); } //copy ChartElements to marks: for(var k=0;k< currentChartModel.chartElements.length;k++) { marksArray[k]=renderChartElementWithPlot(currentChartModel.chartElements[k],ergebniselementOrdnr); /*Plot.barX(rs_table0, { x: "gesamt", y: "eintrag", fill: "blue" } */ } myOptions["marks"].push(marksArray); var svgPlot=Plot.plot(myOptions); var srcPlot=JSON.stringify(myOptions); if(document.getElementById("plotCodeTextArea")) document.getElementById("plotCodeTextArea").innerHTML=srcPlot; document.getElementById(targetDiv).innerHTML=""; document.getElementById(targetDiv).appendChild(svgPlot); //return svgPlot; } function renderChartSVGWithD3 (currentChartModel,targetDiv,ergebniselementOrdnr) { console.log("using D3JS"); var svgD3=new Object; for(var k=0;k< currentChartModel.chartElements.length;k++) { svgD3=renderChartElementWithD3(currentChartModel,k,targetDiv,ergebniselementOrdnr); } //document.getElementById(targetDiv).innerHTML=""; //document.getElementById(targetDiv).appendChild(svgD3); } function renderChartElementWithD3(currentChartModel,chartElemNr,targetDiv,ergebniselementOrdnr) { // append the svg canvas to the page var margin = { top: 10, right: 20, bottom: 10, left: 20 }; //var margin = { top: 0, right: 50, bottom: 0, left: 0 }, var width = Number(getChartPropertyFromModel(currentChartModel.chartPropertiesUsed,"width")) ;//margin.left - margin.right; var height = Number(getChartPropertyFromModel(currentChartModel.chartPropertiesUsed,"height"));//margin.top - margin.bottom; if(width <20) width=630; if(height <20) height=430; var clearCanvas=document.getElementById(targetDiv); while (clearCanvas.firstChild) { clearCanvas.removeChild(clearCanvas.firstChild); } //targetDiv chartElem=currentChartModel.chartElements[chartElemNr]; if(chartElem) { var chartType=chartElem.vizTypeUniquename; var rsIndexNr=ergebniselementOrdnr; /*if(rs.length==1) { //if only 1 datasource is given, the indexNr is ignored //this way a chartModel can be used in a macro *and* a single view rsIndexNr=0; }*/ var myDatasourceRs=rs[rsIndexNr]; var data=filld3data(rs[rsIndexNr],rsColumnMetaData[rsIndexNr],chartElem); console.log("Mark-option for "+chartType); switch (chartType) { case "sankey": var mySvg = d3.select("#"+targetDiv).append("svg") .attr("width", width + margin.left + margin.right) .attr("height", height + margin.top + margin.bottom) .attr("viewBox", [0,0, width+ margin.left + margin.right, height+ margin.top + margin.bottom]) .append("g") .attr("transform", "translate(" + margin.left + "," + margin.top + ")") ; mySvg=makeSankeyD3(currentChartModel.chartPropertiesUsed,mySvg,data,rsColumnMetaData[chartElem.datasource],chartElem); break; case "worldmap": var mySvg = d3.select("#"+targetDiv).append("svg") .attr("width", width + margin.left + margin.right) .attr("height", height + margin.top + margin.bottom) .attr("viewBox", [0,0, width+ margin.left + margin.right, height+ margin.top + margin.bottom]) .append("g") .attr("transform", "translate(" + margin.left + "," + margin.top + ")") ; mySvg=makeWorldmapD3(currentChartModel.chartPropertiesUsed,mySvg,data,rsColumnMetaData[chartElem.datasource],chartElem); break; case "pie": var backgroundColorSelected=getChartPropertyFromModel(currentChartModel.chartPropertiesUsed,"backgroundColor",false); var mySvg = d3.select("#"+targetDiv).append("svg") .attr("width", width + margin.left + margin.right) .attr("height", height + margin.top + margin.bottom) .attr("viewBox", [-(width+ margin.left + margin.right) / 2, -(height+ margin.top + margin.bottom) / 2, width+ margin.left + margin.right, height+ margin.top + margin.bottom]) .style("background-color", backgroundColorSelected) .append("g") ; mySvg=makePie_d3(currentChartModel.chartPropertiesUsed,mySvg,data,chartElem,width,height); break; case "sunburst": width = 928; height = width; var mySvg = d3.select("#"+targetDiv).append("svg") .attr("width", width + margin.left + margin.right) .attr("height", height + margin.top + margin.bottom) .attr("viewBox", [-(width+ margin.left + margin.right) / 2, -(height+ margin.top + margin.bottom) / 2, width+ margin.left + margin.right, height+ margin.top + margin.bottom]) .append("g") .attr("transform", "translate(" + margin.left + "," + margin.top + ")") ; mySvg=makeSunburstD3(currentChartModel.chartPropertiesUsed,mySvg,data,rsColumnMetaData[chartElem.datasource],chartElem); break; default: alert("Unknown chart type"); break; } } return mySvg; } function makePie_d3(myCommonChartProperties,svg,data,chartElem,width,height) { //const width = 928; //const height = Math.min(width, 500); // Create the color scale. const radius = Math.min(width, height) / 2; var innerRadiusPercent = parseFloat(getChartPropertyFromModel(myCommonChartProperties,"innerRadius"),false); var innnerRadiusComputed= radius * innerRadiusPercent / 100; var myPalette=getChartPropertyFromModel(myCommonChartProperties,"scheme",false); var textColor=getChartPropertyFromModel(myCommonChartProperties,"stroke",false); var cornerRadius=getChartPropertyFromModel(myCommonChartProperties,"cornerRadius",false); var labelRadiusFactor=parseFloat(getChartPropertyFromModel(myCommonChartProperties,"labelRadiusFactor",false))/100; if(textColor=="") textColor="black"; /*const color = d3.scaleOrdinal() .domain(data.map(d => d.dimension1)) .range(d3.quantize(t => d3.interpolateSpectral(t * 0.8 + 0.1), data.length).reverse()) const color = d3.scaleOrdinal() .domain(data.map(d => d.dimension1)) .range(["#8cc277","#78a767","#1d71b8","#5b89c7","#2fac66"]); //Palette HMS */ //const color = d3.scaleOrdinal(d3.schemeAccent); const color = d3.scaleOrdinal(getD3ColorScheme(myPalette)); /*const color = d3.scaleOrdinal() .domain(data.map(d => d.dimension1)) .range(d3.schemePastel2) ; */ // Create the pie layout and arc generator. const pie = d3.pie() .sort(null) .value(d => d.measure1); const arc = d3.arc() .innerRadius(innnerRadiusComputed ) .outerRadius(radius - 1) .cornerRadius(cornerRadius); const labelRadius = arc.outerRadius()() * labelRadiusFactor; // A separate arc generator for labels. const arcLabel = d3.arc() .innerRadius(labelRadius) .outerRadius(labelRadius+200); const arcs = pie(data); //svg.width=width; //svg.height=width; //d3.select(svg).attr("viewBox",[-width / 2, -height / 2, width, height]); //svg.style="max-width: 100%; height: auto; font: 10px sans-serif;"; /*const svg = d3.create("svg") .attr("width", width) .attr("height", height) .attr("viewBox", [-width / 2, -height / 2, width, height]) .attr("style", "max-width: 100%; height: auto; font: 10px sans-serif;"); */ // Add a sector path for each value. svg.append("g") .attr("stroke", "white") .selectAll() .data(arcs) .join("path") .attr("fill", d => color(d.data.dimension1)) .attr("d", arc) .append("title") .text(d => `${d.data.dimension1}: ${d.data.measure1.toLocaleString("de-DE")}`); // Create a new arc generator to place a label close to the edge. // The label shows the value if there is enough room. svg.append("g") .attr("text-anchor", "middle") .selectAll() .data(arcs) .join("text") .attr("transform", d => `translate(${arcLabel.centroid(d)})`) .call(text => text.append("tspan") .attr("y", "-0.4em") //.attr("font-weight", "bold") .attr("stroke", textColor) .attr("fill", textColor) .text(d => d.data.dimension1)) .call(text => text.filter(d => (d.endAngle - d.startAngle) > 0.25).append("tspan") .attr("x", 0) .attr("y", "0.7em") .attr("fill-opacity", 0.7) .text(d => d.data.measure1.toLocaleString("de-DE"))); //return svg.node(); return svg.node(); } function makeWorldmapD3(myCommonChartProperties,mySvg,data,metaData,chartElem) { // load the data var captionEmptyTarget=getChartPropertyFromModel(myCommonChartProperties,"null_value_mask"); renderWorldMap(myCommonChartProperties,mySvg,data); } function renderWorldMap(myCommonChartProperties,mySvg,data) { const worldWidth = 670; const worldHeight = 450; const worldTooltip = d3.select(".vizTooltip"); const worldColor = d3.scaleSequential(d3.interpolateBlues) .domain([0, 1]); // Domain matches the output of logColor const worldLogColor = d3.scaleLog() .domain([1, 41227]) // Adjust this domain to fit your data range .range([0, 1]); const worldSvg = d3.select("#world-map") .attr("width", worldWidth) .attr("height", worldHeight); const worldProjection = d3.geoMercator() .scale(100) .translate([worldWidth / 2, worldHeight / 1.5]); const worldPath = d3.geoPath().projection(worldProjection); var d=getWorldMapData(data); // Load the world data files Promise.all([ /*d3.json("https://raw.githubusercontent.com/holtzy/D3-graph-gallery/master/DATA/world.geojson"),*/ /*d3.csv("/superx/viz_worldmap/data.csv", d => ({ iso3: d.iso3, value: +d.value }))*/ d3.json("../xml/js/viz/world.geojson"), /*getLocalJson("/superx/xml/js/viz/world_superx2.geojson"),*/ d ]).then(([worldGeojson, worldData]) => { const worldDataMap = new Map(worldData.map(d => [d.iso3, d.value])); mySvg.append("g") .selectAll("path") .data(worldGeojson.features) .enter().append("path") .attr("d", worldPath) .attr("fill", d => { const value = worldDataMap.get(d.id); // Use `d.id` to access ISO 3 codes if (value === 0) return "#ccc"; // Handle zero values separately return value ? worldColor(worldLogColor(value)) : "#ccc"; }) .on("mouseover", function (event, d) { const value = worldDataMap.get(d.id); worldTooltip.transition() .duration(200) .style("opacity", .9); worldTooltip.html(d.properties.name + "
" + (value ? value : "No data")) .style("left", (event.pageX) + "px") .style("top", (event.pageY - 28) + "px"); }) .on("mouseout", function () { worldTooltip.transition() .duration(500) .style("opacity", 0); }); }).catch(error => { console.error('Error loading or parsing data:', error); }); async function getLocalJson(url) { try { const response = await fetch(url); if (!response.ok) { throw new Error(`Serverantwort: ${response.status}`); } const myJson = await response.json(); return myJson; } catch (error) { console.log(error.message); } } function getWorldMapData(data) { var myData=[]; var zs=""; for (var i = 0; i < data.length; i++) { myData[i] = { "iso3": data[i].dimension1, "value": data[i].measure1 }; } return myData; } } function makeSankeyD3(myCommonChartProperties,mySvg,data,metaData,chartElem) { // load the data var captionEmptyTarget=getChartPropertyFromModel(myCommonChartProperties,"null_value_mask"); if(captionEmptyTarget=="") captionEmptyTarget="Leer"; var sNodes=getSankeyNodes(data,captionEmptyTarget); //graph.nodes; var sLinks=getSankeyLinks(sNodes,data); //graph.links; renderSankey(myCommonChartProperties,mySvg,sNodes,sLinks); //var myChartSVG = SankeyChart(sNodes,sLinks); } function getSankeyNodes(data,captionEmptyTarget) { var myNodes=[]; var distinctSource = []; var zs=""; for (var i = 0; i < data.length; i++) { if(zs.indexOf("_" + data[i].dimension1 +"_")<0) { distinctSource.push(data[i].dimension1); zs+="_" + data[i].dimension1 +"_"; } } for (var i = 0; i < data.length; i++) { if(zs.indexOf("_" + data[i].dimension2 +"_")<0) { distinctSource.push(data[i].dimension2); zs+="_" + data[i].dimension2 +"_"; } } for (var i = 0; i < distinctSource.length; i++) { myNodes[i] = { "node": i, "name": distinctSource[i] }; console.log("Abschluss: "+distinctSource[i]); } //Kein Abschluss: myNodes[i] = { "node": i, "name": captionEmptyTarget }; return myNodes; } function getSankeyLinks(myNodes,data) { var myLinks=[]; var linkIndex=0; for (var i = 0; i < data.length; i++) { if(data[i].dimension2 !="") { myLinks[linkIndex]={ "source": getSankeyNodeIndex(myNodes,data[i].dimension1), "target": getSankeyNodeIndex(myNodes,data[i].dimension2), "value":data[i].measure1 }; linkIndex++; } else { myLinks[linkIndex]={ "source": getSankeyNodeIndex(myNodes,data[i].dimension1), "target": myNodes.length-1, "value":data[i].measure1 }; linkIndex++; } } return myLinks; } function getSankeyNodeIndex(myNodes,name) { var myIndex=0; for (var i = 0; i < myNodes.length; i++) { if(myNodes[i].name==name) myIndex=i } return myIndex; } function getMeasureCaption(chartElem,metaData) { var measureCaption=""; for(var k=0;k o.vizTypePropertyUniquename == "dimension1"); var dimension1Caption=dimension1Prop.caption; var dimension1Fldname=dimension1Prop.propertyValue; var dimension2Prop = ""; var dimension2Caption=""; var dimension2Fldname=""; var dimension2Prop=dsChartElement.elementTypeProperties.find(o => o.vizTypePropertyUniquename == "dimension2"); if(dimension2Prop) { dimension2Caption=dimension2Prop.caption; dimension2Fldname=dimension2Prop.propertyValue; } var measure1Prop = dsChartElement.elementTypeProperties.find(o => o.vizTypePropertyUniquename == "measure1"); var measure1Caption=measure1Prop.caption; var measure1Fldname=measure1Prop.propertyValue; var skel= new chartSkeleton(ergebniselementOrdnr, title, subtitle, dimension1Fldname, dimension1Caption, dimension2Fldname, dimension2Caption, measure1Fldname, measure1Caption, measure2Fldname, measure2Caption ); chartSkeleton(nr, title, subtitle, dimension1Fldname, dimension1Caption, hasDimension2, dimension2Fldname, dimension2Caption, measure1Fldname, measure1Caption, hasMeasure2, measure2Fldname, measure2Caption } */ function closeModalCardDetail(ergebniselementOrdnr) { var myModalCard=document.getElementById("modalCardDetail"+ergebniselementOrdnr); myModalCard.classList.remove('is-active'); } function getEchartOptionsBarLine(currentChartModel,myDataset,chartType,titleText) { //TODO: bar_x und y abfangen' var chartTypes = chartType.split(/_/); var orientation=chartTypes[2]; var measure1Axis="y"; var dimension1Axis="x"; var xAxisType="category"; var yAxisType="value"; if(orientation=="x") { measure1Axis="x"; dimension1Axis="y"; yAxisType="category"; xAxisType="value"; } //var measure1Fldname=getChartPropertyValue(currentChartModel.chartPropertiesUsed,measure1Axis); var measure1Fldname=getChartElementPropertyValueFromModel(currentChartModel,1,measure1Axis); var dimension1Fldname=getChartElementPropertyValueFromModel(currentChartModel,1,dimension1Axis); //var dimension1Fldname=getChartPropertyValue(currentChartModel.chartPropertiesUsed,dimension1Axis); var subtitleText=getChartPropertyValue(currentChartModel.chartPropertiesUsed,"subtitle"); var scheme = getChartPropertyValue(currentChartModel.chartPropertiesUsed,"scheme"); var myPalette=getSchemeArray(scheme); var encodeObj={x:dimension1Fldname,y:measure1Fldname}; if(orientation=="x") encodeObj={y:dimension1Fldname,x:measure1Fldname}; var option = { dataset: myDataset, /*klappt nicht, noch testen: transfxAxis: { typeorm: { type: 'sort', config: { dimension: "dim_studiengang_fb", order: 'asc' } } ,*/ title: { text: titleText, subtext: subtitleText, left: "center", top: "top", textStyle: { fontSize: 20 }, subtextStyle: { fontSize: 15 } }, grid: { top: "16%", left: "20%" }, tooltip: { trigger: "axis", axisPointer: { type: "shadow" },/* formatter: function (value, index) { return numberFormatter(value,"value"); }*/ valueFormatter: (value) => numberFormatter(value,"value") }, xAxis: { type:xAxisType, //horizontal oder vertikal //type: 'category', axisLabel: { inside: false, margin: 15, fontSize: 12, width:"100px", rotate: 30, formatter: function (value, index) { return numberFormatter(value,xAxisType); } } }, yAxis: { //type:'value', type: yAxisType, axisLabel: { inside: false, margin: 5, fontSize: 12, width:"50px", formatter: function (value, index) { return numberFormatter(value,yAxisType); } } }, series: [ { type: chartTypes[1], //bar,line encode: encodeObj, barWidth: '30%', showBackground: true, backgroundStyle: { color: '#dfe4f2' }, margin: 50, fontSize: 14, colorBy: 'data', lineStyle: { width: 7 }, label: { show: true }, labelLayout(params) { return getLabelLayout(params,orientation) } } ], color:myPalette }; return option; } /* Labels bei Balkendiagramm je nach Orientierung - horizontal: rechts neben Balken - vertikal: zentriert im Balken */ function getLabelLayout(params,orientation) { if(orientation=="x") { return { x: params.rect.x +params.rect.width+ 30, y: params.rect.y + params.rect.height / 2, verticalAlign: 'middle', align: 'right' }; } else return {verticalAlign: 'middle'}; } function getEchartOptionsNative(currentChartModel,myDataset) { var options=currentChartModel.chartElements[0].sourceCode; options.dataset=myDataset; //var dataset ={dataset}; //dataset.source=myDataset; //options=Object.assign(myDataset,options); return options; } function getEchartOptionsPie(currentChartModel,myDataset) { var measure1Fldname=getChartElementPropertyValueFromModel(currentChartModel,"1","measure1"); var dimension1Fldname=getChartElementPropertyValueFromModel(currentChartModel,"1","dimension1"); var titleText=getChartPropertyValue(currentChartModel.chartPropertiesUsed,"caption"); var scheme = getChartPropertyValue(currentChartModel.chartPropertiesUsed,"scheme"); var myPalette=getSchemeArray(scheme); var option = { dataset: { source: myDataset }, title: { text: titleText, subtext: "", left: "left", top: "top", textStyle: { fontSize: 20 }, subtextStyle: { fontSize: 15 } }, series: [ { type: 'pie',// sunburst /*encode: { value: measure1Fldname, name: dimension1Fldname },*/ tooltip: { trigger: "item" }, stillShowZeroSum: false, label: { show: true, formatter: '{c}', width:200 }, fontSize: 12, radius: ['30%', '80%'], //1. Parameter inside radius, macht ihn zum Donut. 2.Parameter definiert den Anteil des Kreises am ganzen Viewport" color: myPalette, itemStyle: { //borderRadius: [20, 5, 5, 10], //abgerundete Ecken der Tortenstücke borderColor: '#fff', borderWidth: 2 } } ] }; return option; } function getChartPropertyValue(propArray,propName) { var propertyValue=""; for (var i=0;i obj.elemID == elemID); var myChartElem=filtered[0]; if(myChartElem.elementTypeProperties && myChartElem.elementTypeProperties.length) { for(var k=0;k < myChartElem.elementTypeProperties.length;k++) { myVizTypeProperty=myChartElem.elementTypeProperties[k]; if(myVizTypeProperty.vizTypePropertyUniquename==propUniquename) { retVal=myVizTypeProperty.propertyValue; } } } } return retVal; } function getChartPropertyFromModel(myChartProperties,name,isCommon) { var propertyValue=""; if(myChartProperties && myChartProperties.length>0) { let prop = myChartProperties.find(o => o.name === name); if(!prop) prop = myChartProperties.find(o => o.vizTypePropertyUniquename == name); if(prop) propertyValue=prop.propertyValue; } //if no value is set from model, retrieve the default value: if(propertyValue=="" && isCommon) propertyValue=getCommonChartProperty(name); return propertyValue; } function getCommonChartProperty(name) { var propertyValue=""; if(document.forms["chartPropertiesForm"] && document.forms["chartPropertiesForm"].elements[name]) { propertyValue=document.forms["chartPropertiesForm"].elements[name].value; } if(propertyValue=="") { let prop = commonChartProperties.find(o => o.name === name); if(prop.defaultValue!="") { propertyValue=prop.defaultValue; } } /*for (var i=0;i { for (var col in row) { console.log(col +"-"+row[col]); if(col==dimension1) dimension1Value=row[col]; if(col==dimension2) dimension2Value=row[col]; if(col==measure1) measure1Value=row[col]; } data.push(new d3dataRow(rownr,dimension1Value,dimension2Value,measure1Value)); rownr++; } ); /* console.log(rownr +"-" + dimension1Value +"-" +dimension2Value +"-" +measureDimValue); selectionRs.push(new d3dataRow(rownr,dimension1Value,dimension2Value,measureDimValue)); //identify max String length to compute x axis size if(dimension1Value.length >maxLenDimension1) maxLenDimension1=dimension1Value.length; //the same for values: if(measureDimValue >maxMeasure) maxMeasure=measureDimValue; } //TODO:Sorting and filtering */ return data; } function isChartPropertyValidForChartelements(prop,currentChartModel) { var propValid=false; if(prop.isGeneric==1) return true; var nrOfChartElements=currentChartModel.chartElements.length; for(var k=0;k < nrOfChartElements;k++) { var usedVizTypeUniquename=currentChartModel.chartElements[k].vizTypeUniquename; for(var i=0;i < vizTypeProperties.length;i++) { if(vizTypeProperties[i].propUniquename==prop.name && vizTypeProperties[i].typeUniquename==usedVizTypeUniquename) propValid=true; } } return propValid; } function getD3ColorScheme(name,size) { //blues|greens|greys|oranges|purples|reds|paired|set1|pastel1|pastel2|tableau10|category10|accent|dark2 if(size==null || size==0) size=9; switch (name) { case "blues": return d3.schemeBlues[size]; break; case "greens": return d3.schemeGreens[size]; break; case "greys": return d3.schemeGreys[size]; break; case "oranges": return d3.schemeOranges[size]; break; case "purples": return d3.schemePurples[size]; break; case "reds": return d3.schemeReds[size]; break; case "accent": return d3.schemeAccent; break; case "paired": return d3.schemePaired; break; case "set1": return d3.schemeSet1; break; case "category10": return d3.schemeCategory10; break; case "dark2": return d3.schemeDark2; break; case "pastel1": return d3.schemePastel1; break; case "pastel2": return d3.schemePastel2; break; case "tableau10": return d3.schemeTableau10; break; case "custom1": return ["#5b89c7","#2fac66","#8cc277","#78a767","#1d71b8"]; break; default: return d3.schemePastel2; break; } } function vizTabelleComboOderSichtLaden(maskentid,fname, caption,fnameEscaped,zeilenanzahl,feldart,referrerForm) { Feldname = fname; var callurl = '/superx/servlet/SuperXmlMaske'; callurl += "?tid=" + maskentid + "&getJSON_" + getEncoded(Feldname) + '=xxxxxx-xxxxxx@'; var params = ""; var myElements= new Array(); myElements=document.forms["Weiterverarbeitung"].elements; var e=document.forms["Weiterverarbeitung"].elements[fname]; for (var i = 1; i < felder.length; i++) { e = myElements[felder[i]["htmlname"]]; if (e) { var t = e.type; var name = felder[i]["name"]; if (t == 'text') { //todo bei startsWith select_ label_ auch überspringen if (e.value != '') //leere Felder müssen auch übergeben werden MB!! // 1/2016 MB dies geht nicht weil ISO kodiert //params+="&"+felder[i]["cb_name"]+"="+encodeURIComponent(e.value); params += "&" + getEncoded(felder[i]["htmlname"]) + "=" + getEncoded(e.value); else params += "&" + getEncoded(felder[i]["htmlname"]) + "=--leer--"; } } } console.log("PARAMS:"+params); //return false; var currentFieldValue=document.forms['Weiterverarbeitung'].elements[Feldname].value; /*var splitchar=","; if(currentFieldValue.indexOf("|")>-1) splitchar="\|"; var currentFieldValueArray = currentFieldValue.split(splitchar); var currentFieldValueCount=currentFieldValueArray.length; */ params=encodeURIComponent(params); //alert(params); var jspPage="maske_combo_laden.jsp"; if(feldart==12) jspPage="maske_sicht_laden.jsp"; var editurl="/superx/edit/kern/"+jspPage+"?tid="+maskentid+ "&Feldname="+getEncoded(fname)+"&previousValue="+currentFieldValue; editurl +="&zeilenanzahl="+zeilenanzahl+"&referrerForm=Weiterverarbeitung¶ms="+params; neu2=window.open(editurl,"_blank","directories=no,location=no,menubar=no,scrollbars=yes,resizable=yes,toolbar=no,width=800,height=660"); } function applyFunction(theValue,theFunction) { switch (theFunction) { case "switchWord1and2ff": var ret=switchWord1and2ff(theValue); break; case "justWord1": var ret=justWord1(theValue); break; case "abbreviate": var ret=abbreviate(theValue,20); break; default: var ret=theValue; break; } return ret; } function switchWord1and2ff(theString) { //erzeugt z.B. aus "WiSe 2020/2021" den Wert "2020/2021", zum Sortieren var theWords = theString.split(/ /); var word1=theWords[0]; var word2=""; var ret=""; if(theWords.length >1) { for(var k=1;k < theWords.length;k++) { word2+= theWords[k]; } ret +=word2; } ret+=" "+ word1; return ret.trim(); } function justWord1(theString) { //nur erstes Wort, zum Sortieren var word1End=-1; var i=0; var endFound=false; do{ var myChar=theString.substr(i,1); if(myChar=="|" || myChar==" "|| myChar=="-") { endFound=true; word1End=i; } else i++; } while (endFound==false && i<=theString.length); if(word1End==-1) word1End=theString.length; return theString.substr(0,word1End); } function abbreviate(theString,theMaxLength) { //nur erste x Zeichen if(theString.length > theMaxLength) { var theCut = theString.substr(0,theMaxLength-3)+"..."; return theCut; } else return theString.trim(); } function getColumnCaption(columnName) { let rsMetaDataLen = rsMetaData.length; var colCaption=columnName; for (let i = 0; i < rsMetaDataLen; i++) { if(rsMetaData[i].colname ==columnName) colCaption=rsMetaData[i].colcaption; } return colCaption; } function getSchemeArray(schemeName) { var schemeArray=new Array(); switch (schemeName) { case "abgrp": /*Bachelor: BA blau #374ca und 80 % , LA BA #5e70ba Master: #64a6d9 #8cb7e1 Promotion: #7aa2ba Sonstige: #98b4c9*/ schemeArray=['#374ca','#5e70ba','#64a6d9','#8cb7e1','#7aa2ba','#98b4c9','#ff933e']; break; case "fak": schemeArray=['#488a7c','#374ca9','#ffd705','#a68eca','#e84035','#64a6d9','#ff933e','#ee79ad','#7aa2ba','#c3df35','#9bceab','#782f88','#96BFFF']; break; case "unique": schemeArray=['#004c93']; break; case "dichotom": schemeArray=['rgb(97,162,124)','#c3df35','#9d96f5','#e7bcf3']; break; case "quadroColor": schemeArray=['#374ca9','#5e70ba','#8794cb','#afb7dc']; break; case "blandLocalized": myBland=9; for(var j=0;j < 17;j++) { if(j==myBland) schemeArray[j]='#004c93'; else schemeArray[j]='#666666'; } break; case "colorGrades": //cooles Tool:https://mdigi.tools/lighten-color/ in 7% Schritten heller schemeArray=['#374ca9','#3c53b8','#455cc3','#556ac8','##6477cc','#7384d1','#8291d6','#919fdb','#a0ace0','#afb9e5','#bec6ea','#cdd4ef','#dce1f4','#eceef9','#f4f6fb','#f6f7fc']; break; default: schemeArray=[ '#ec7206', '#61a27c', '#b8103b', '#feca00', '#FFDB5C', '#ff9f7f', '#fb7293', '#E062AE', '#E690D1', '#e7bcf3', '#9d96f5', '#8378EA', '#96BFFF' ]; break; } return schemeArray; } function openDashboardTab(tabnr,maskennr,optional_filter_name,optional_filter_value,myOptionalFilters) { var myForm=document.forms["Weiterverarbeitung"]; myForm.elements["tid"].value=maskennr; myForm.elements["Tabnr."].value=tabnr; myForm.elements["reuseresult"].value="false"; //zuerst alle Filter resetten: if(myForm.elements["Booklet-Stylesheet"]) { myForm.elements["Booklet-Stylesheet"].value=""; } if(myOptionalFilters.length>0) { for(var j=0;j < myOptionalFilters.length;j++) { var optionalFilterFldName=myOptionalFilters[j+1]; console.log("Resetting "+optionalFilterFldName); if(myForm.elements[optionalFilterFldName]) { myForm.elements[optionalFilterFldName].value=""; } } } if(optional_filter_name != "") { myForm.elements[optional_filter_name].value=optional_filter_value; } myForm.submit(); } function openKachelDetails(ergebniselementOrdnr,formName,maskeninfoTID,grafikUniquename,tablestylesheet,reuseResults) { document.forms[formName].elements["tid"].value=maskeninfoTID; document.forms[formName].elements["Grafik"].value=grafikUniquename; document.forms[formName].elements["tablestylesheet"].value=tablestylesheet; if(document.forms[formName].elements["##line##"]) { document.forms[formName].elements["##line##"].value=""; } if(!reuseResults) { document.forms[formName].elements["reuseresult"].value="false"; } document.forms[formName].target="_blank"; document.forms[formName].submit(); } function exportVizBooklet(contenttype,stylesheet) { document.forms['Weiterverarbeitung'].stylesheet.value = stylesheet; //document.forms['Weiterverarbeitung'].tablestylesheet.value = stylesheet; document.forms['Weiterverarbeitung'].contenttype.value = contenttype; document.forms['Weiterverarbeitung'].target = '_blank'; document.forms['Weiterverarbeitung'].submit(); } function numberFormatter(value,axisType,digits,usedLocale) { //TODO: digits auswerten if(axisType=="value") { var myusedLocale="de-DE"; //default if(!usedLocale || usedLocale=="") myusedLocale=usedLocale; return new Intl.NumberFormat(myusedLocale).format(value); } else return value ; }