// Copyright 2017 Istituto Nazionale di Fisica Nucleare // // Licensed under the EUPL import * as assert from "assert"; import * as $ from "jquery"; import * as Help from "./helper"; import G = require("./globals"); import { DrawImage } from "./drawImage"; import { DrawChart } from "./drawChart"; /*export function generateTree(xmlDoc: Document) { let tree: any = []; let first = true; let oldFolderParent: string = ""; let oldFolder: string = ""; //inizio leggendo tutti gli elementi da inserire nell'albero (caratterizzati //dall'avere un url di riferimento) let entry = $("D:href", xmlDoc); //per ogni elemento controllo se si tratta di una cartella o di un documento for (let i: number = 0; i < entry.length; i++) { let path: string[] = entry[i].childNodes[0].nodeValue.split(""); //cartella, creo l'oggetto corrsipondente if (path[path.length - 1] == "/") { let folderName: string[] = entry[i].childNodes[0].nodeValue.split("/"); let Folder = { text: folderName[folderName.length - 2], nodes: [] }; //posiziono la radice del file system, ne memorizzo il path e il padre if (first) { tree.push(Folder); first = false; oldFolder = entry[i].childNodes[0].nodeValue; oldFolderParent = oldFolder.slice(0, oldFolder.lastIndexOf(folderName[folderName.length - 2])); //per ogni cartella determino la relazione con la cartella precedente } else { let newFolder: string = entry[i].childNodes[0].nodeValue; let newFolderParent: string = newFolder.slice(0, newFolder.lastIndexOf(folderName[folderName.length - 2])); //cartella sorella con quella memorizzata if (newFolderParent == oldFolderParent) { oldFolder = newFolder; insertOBJinFS(Folder, tree, folderName, 0); //cartella figlia di quella memorizzata } else if (newFolderParent == oldFolder) { oldFolder = newFolder; oldFolderParent = newFolderParent; insertOBJinFS(Folder, tree, folderName, 0); //nessuno dei casi precedenti } else { //arretro nell'albero fino a trovare lo stesso padre. Per fare questo //tolgo al padre memorizzato in precedenza prima "/" poi il nome dell' //ultima cartella while (newFolderParent != oldFolderParent) { oldFolderParent = oldFolderParent.slice(0, oldFolderParent.length - 1); oldFolderParent = oldFolderParent.slice(0, oldFolderParent.lastIndexOf("/") + 1); } oldFolder = newFolder; insertOBJinFS(Folder, tree, folderName, 0); } } //documento, creo l'oggetto corrispondente e lo inserisco nell'albero } else { let fileName: string[] = entry[i].childNodes[0].nodeValue.split("/"); let filePath: string = entry[i].childNodes[0].nodeValue; let File = { text: fileName[fileName.length - 1], icon: "glyphicon glyphicon-file", selectedIcon: "glyphicon glyphicon-file", url: filePath }; insertOBJinFS(File, tree, fileName, 1); } } return tree; }*/ //funzione che posiziona l'oggetto passato in input nell'albero /*function insertOBJinFS(objfs, tree, objfsName, type) { //determino la profondità dell'oggetto (se è un file devo aggiungere 1 a causa di "/") let depth: number = objfsName.length; if (type) depth++; //in base alla profondità determino a quale oggetto agganciare quello in input let treePosition: any; let l: number = tree.length - 1; switch (depth) { case 6: treePosition = tree; break; case 7: treePosition = tree[l].nodes; break; case 8: treePosition = tree[l].nodes[tree[l].nodes.length - 1].nodes; break; case 9: treePosition = tree[l].nodes[tree[l].nodes.length - 1].nodes[tree[l].nodes[tree[l].nodes.length - 1].nodes.length - 1].nodes; break; case 10: treePosition = tree[l].nodes[tree[l].nodes.length - 1].nodes[tree[l].nodes[tree[l].nodes.length - 1].nodes.length - 1] .nodes[tree[l].nodes[tree[l].nodes.length - 1].nodes[tree[l].nodes[tree[l].nodes.length - 1].nodes.length - 1].nodes.length - 1].nodes; break; default: break; } treePosition[treePosition.length - 1].nodes.push(objfs); }*/ //funzione che dato l'url di un file, lo apre e lo legge passandone il contenuto //alla funzione readData(). Questa funzione è invocata quando viene selezionato //un file dall'albero /*export function openFileFromServer(url) { let fileName: string[] = url.split("/"); console.log("Try to open " + fileName[fileName.length - 1] + " ..."); let txtFile: any = new XMLHttpRequest(); txtFile.open("GET", url, true); txtFile.onreadystatechange = function () { if (txtFile.readyState === 4) { if (txtFile.status === 200) { readImage(txtFile.responseText); } } }; txtFile.send(null); }*/ // version working on an array of numbers, obtained from the array of string lines function get_metadata_num(image: DrawImage, lines: number[]): void { let metadata = G.Metadata.getInstance(); //let image = G.Image.getInstance(); metadata.xMin = 0; metadata.yMin = 0; metadata.xMax = 0; metadata.yMax = 0; metadata.step = 0; //dimensione di un pixel in micorn metadata.direction = G.ReadDirection.u; //direzione di lettura //scorro l'array soffermandomi solo sulle righe "intestazione delle x". Devo //determinare ascisse e cordinate minime e massime, il passo e la direzione di //scansione for (let i = 0; i < lines.length; i++) { if (Help.isAnXHeader(lines[i], image)) { if (metadata.xMin == 0) { //se sono alla prima intestazione salvo la x e la y metadata.xMin = lines[i]; metadata.yMin = lines[i + 1]; i++; } else { //definisco passo e direzione di scansione dalla seconda intestazione if (lines[i] == metadata.xMin) { metadata.direction = G.ReadDirection.c; metadata.step = Math.abs(metadata.yMin - lines[i + 1]); // the unary + converts to number //se sto leggendo per colonne determino metadata.xMax leggendo dalla fine for (let j: number = lines.length; j > i; j--) { //se la riga è "intestazione x" memorizzo metadata.xMax e lo confronto con metadata.xMin if (Help.isAnXHeader(lines[j], image)) { metadata.xMax = lines[j]; if (metadata.xMax < metadata.xMin) { let t: number = metadata.xMax; metadata.xMax = metadata.xMin; metadata.xMin = t; } break; } } } else { metadata.direction = G.ReadDirection.r; metadata.step = Math.abs(metadata.xMin - lines[i]); // the unary + converts to number //se sto leggendo per righe determino metadata.yMax leggendo dalla fine for (let j: number = lines.length; j > i; j--) { //se la riga è "intestazione y" memorizzo metadata.yMax e lo confronto con metadata.yMin if (Help.isAnYHeader(lines[j], image)) { metadata.yMax = lines[j]; if (metadata.yMax < metadata.yMin) { let t: number = metadata.yMax; metadata.yMax = metadata.yMin; metadata.yMin = t; } break; } } } break; } } } //A seconda della direzione di lettura determino o metadata.yMin e metadata.yMax, o metadata.xMin e metadata.xMax for (let i: number = 2; i < lines.length; i++) { if (metadata.direction == G.ReadDirection.c) { //se leggo per colonne devo deterinare metadata.yMin e metadata.yMax //mi soffermo sulle righe "intestazione y" if (Help.isAnYHeader(lines[i], image)) { if (metadata.yMin > lines[i]) { metadata.yMin = lines[i]; } if (metadata.yMax < lines[i]) { metadata.yMax = lines[i]; } } //alla terza colonna posso uscire perché ho già tutte le informazioni if (lines[i] == metadata.xMin + metadata.step * 2) { break; } } else { //se leggo per righe devo deterinare metadata.xMin e metadata.xMax //mi soffermo sulle righe "intestazione x" if (Help.isAnXHeader(lines[i], image)) { if (metadata.xMin > lines[i]) { metadata.xMin = lines[i]; } if (metadata.xMax < lines[i]) { metadata.xMax = lines[i]; } } //alla terza colonna posso uscire perché ho già tutte le informazioni if (lines[i] == metadata.yMin + 2000) { break; } } } } export function get_metadata(image: DrawImage, lines: number[]): void { try { get_metadata_num(image, lines); } catch (e) { throw new Error(e); } } // La funzione readImage() prende in ingresso il file di input memorizzato nella // stringa "fileString". La funzione riempie la matrice "DataMatrix" con i dati // in modo che essi siano memorizzati in un formato più leggibile. Sono ricavate // anche altre variabili necessarie per il resto del codice. export function readImage(image: DrawImage, chart: DrawChart ,content: string): DrawImage { let lines = content.split("\n").map(Number); let metadata = G.Metadata.getInstance(); get_metadata(image, lines); // Risolvo gli shift for (let i = 0; i < lines.length; i++) { if (Help.isAnXHeader(lines[i], image)) { // this is an x-coordinate if (metadata.direction == G.ReadDirection.c && (lines[i] / 1000) % 2 != 0) { // increment the y-coordinate of odd columns lines[i + 1] += metadata.step; } else if (metadata.direction == G.ReadDirection.r && (lines[i + 1] / 1000) % 2 != 0) { // increment the x-coordinate of even rows lines[i] += metadata.step; } } } //Definisco le dimensioni della matrice DataMatrix e la inizializzo let xDim: number; let yDim: number; if (metadata.direction == G.ReadDirection.c) { xDim = (metadata.xMax - metadata.xMin) / metadata.step + 1; yDim = (metadata.yMax - metadata.yMin) / metadata.step - 2; } else { xDim = (metadata.xMax - metadata.xMin) / metadata.step - 2; yDim = (metadata.yMax - metadata.yMin) / metadata.step + 1; } image.width = xDim; image.height = yDim; image.DataMatrix = new Array(xDim); for (let i: number = 0; i < xDim; i++) { image.DataMatrix[i] = new Array(yDim); for (let j: number = 0; j < yDim; j++) { image.DataMatrix[i][j] = new Array(image.depth); for (let k: number = 0; k < image.depth; k++) { image.DataMatrix[i][j][k] = 0; } } } //riempio la matrice DataMatrix eliminando i bordi let x: number, y: number; let write: boolean; for (let i = 0; i < lines.length; i++) { //riga "intestazione x": memorizzo le x e le y del punto e avanzo al conteggio if (Help.isAnXHeader(lines[i], image)) { x = lines[i] - metadata.xMin; y = lines[i + 1] - metadata.yMin; if (x != 0) { x /= metadata.step; } if (y != 0) { y /= metadata.step; } i++; //non è un pixel del bordo e sto leggendo per colonne: i successivi valori //sono da considerare if (metadata.direction == G.ReadDirection.c && y != 0 && y != 1 && y != (metadata.yMax - metadata.yMin) / metadata.step && y != (metadata.yMax - metadata.yMin) / metadata.step + 1) { write = true; y -= 2; //aggiorno la y con i bordi tagliati } else if ( metadata.direction == G.ReadDirection.r && x != 0 && x != 1 && x != (metadata.xMax - metadata.xMin) / metadata.step && x != (metadata.xMax - metadata.xMin) / metadata.step + 1) { //non è un pixel del bordo e sto leggendo per righe: i successivi valori //sono da considerare write = true; x -= 2; //aggiorno la x con i bordi tagliati } else { //pixel del bordo: i valori successivi sono da ignorare write = false; } //conteggio da considerare (non del bordo) } else if (lines[i] < image.headerSetValue && write == true) { image.DataMatrix[xDim - x - 1][yDim - y - 1][lines[i]] += 1; } } //console.log(image.DataMatrix); image.nOfCounts = new Array(xDim); for (let i: number = 0; i < xDim; i++) { image.nOfCounts[i] = new Array(yDim); for (let j: number = 0; j < yDim; j++) { image.nOfCounts[i][j] = Help.sumVect(image.DataMatrix[i][j], 0, image.DataMatrix[i][j].length); } } //console.log(image.nOfCounts); image.maxAbsolute = Help.findMax(image.nOfCounts, { x: 0, y: 0 }, { x: xDim - 1, y: yDim - 1 }); Help.setDataForCompleteChart(image, chart); return image; }