function SmartLayout(neu, con) { this.neuroSL = neu; this.neuroConnSL = con; this.N = this.neuroSL.length; this.blocks = []; this.einfos = []; var parent = this; einfo = function () { this.block = null; this.x = null; this.y = null; } this.Block = function (number) { this.id = number; this.elements = []; this.w = 1; this.h = 1; this.minx = 0; this.miny = 0; this.maxx = 0; this.maxy = 0; this.addElement(number, 0, 0); blocks[this.id] = this; this.map = []; } this.Block.prototype.destroy = function () { blocks[this.id] = 0; this.freeMap(); } this.Block.prototype.freeMap = function () { if (this.map) this.map = []; } this.Block.prototype.needMap = function () { if (this.map) return; this.createMap(); } this.Block.prototype.createMap = function () { this.freeMap(); this.w = this.maxx - this.minx + 1; this.h = this.maxy - this.miny + 1; for (var i = 0; i < this.w * this.h; i++) this.map.push(0); for (var i = 0; i < this.elements.length; i++) { var e = this.elements[i]; this.map[this.w * (parent.einfos[e].y - this.miny) + (parent.einfos[e].x - this.minx)] = 1; } } this.Block.prototype.addElement = function (number, x, y) { this.elements.push(number); parent.einfos[number].x = x; parent.einfos[number].y = y; parent.einfos[number].block = this; } } SmartLayout.prototype.create = function () { ///////////////////////// //////Phase one////////// ///////////////////////// blocks = new Array(this.N); for (var i = 0; i < this.N; i++) { this.einfos.push(new einfo()) } for (var i = 0; i < this.N; i++) this.setElement(i); ///////////////////////// //////Phase two////////// ///////////////////////// var first = null; var el; for (el = 0; el < this.N; el++) { if (blocks[el]) { first = blocks[el]; el++; break; } } while (el < this.N) { if ((first.maxx - first.minx) > (first.maxy - first.miny)) { var y = first.maxy + 2; var x = first.minx; var ex = first.maxx; while (el < this.N) { if (blocks[el]) { var dx = blocks[el].maxx - blocks[el].minx + 2; this.merge(first, blocks[el], x - blocks[el].minx, y - blocks[el].miny); x += dx; if (x > ex) break; } el++; } } else { var x = first.maxx + 2; var y = first.miny; var ey = first.maxy; while (el < this.N) { if (blocks[el]) { var dy = blocks[el].maxy - blocks[el].miny + 2; this.merge(first, blocks[el], x - blocks[el].minx, y - blocks[el].miny); y += dy; if (y > ey) break; } el++; } } } //Pokazanie wartoĊ›ci if (first) // at this stage we have a single block containing all neurons { var i; first.createMap(); for (i = 0; i < first.elements.length; i++) { el = first.elements[i]; } delete first; } } SmartLayout.prototype.canMerge = function (block, block2, dx, dy) { var x1, y1, x2, y2; x1 = Math.max(0, block2.minx - block.minx + dx); x2 = Math.min(block.maxx - block.minx, -block.minx + dx + block2.maxx); if (x1 > x2) return 1; y1 = Math.max(0, block2.miny - block.miny + dy); y2 = Math.min(block.maxy - block.miny, -block.miny + dy + block2.maxy); if (y1 > y2) return 1; var x, y; dx += block2.minx - block.minx; //dx,dy relative to minx,miny dy += block2.miny - block.miny; block.createMap(); block2.createMap(); for (y = y1; y <= y2; y++) { for (x = x1; x <= x2; x++) if (block.map[block.w * y + x] && block2.map[block2.w * (y - dy) + (x - dx)]) return 0; } return 1; } SmartLayout.prototype.merge = function (block, block2, dx, dy) { if (!this.canMerge(block, block2, dx, dy)) return 0; block.freeMap(); for (var i = 0; i < block2.elements.length; i++) { var e = block2.elements[i]; block.addElement(e, this.einfos[e].x + dx, this.einfos[e].y + dy); } block.minx = Math.min(block.minx, dx + block2.minx); block.miny = Math.min(block.miny, dy + block2.miny); block.maxx = Math.max(block.maxx, dx + block2.maxx); block.maxy = Math.max(block.maxy, dy + block2.maxy); block2.destroy(); delete block2; return 1; } SmartLayout.prototype.connectAsInput = function (e, e2) { var b, b2; b = this.einfos[e].block; if (!this.einfos[e2].block) new Block(e2); b2 = this.einfos[e2].block; if (b == b2) { return; } var dx, dy; dx = this.einfos[e].x - this.einfos[e2].x; dy = this.einfos[e].y - this.einfos[e2].y; if (this.merge(b, b2, dx - 1, dy)) return; for (var proba = 1; ; proba++) { if (this.merge(b, b2, dx - 1, dy - proba)) return; if (this.merge(b, b2, dx - 1, dy + proba)) return; } } SmartLayout.prototype.setElement = function (e) { if (this.einfos[e].block != null) { return; } new this.Block(e); var n = this.getNumOfInCon(e); for (var we = 0; we < n; we++) { var e2 = this.getLink(e, we); if (e2 < 0) continue; if (e == e2) continue; this.setElement(e2); this.connectAsInput(e, e2); } } SmartLayout.prototype.getNumOfInCon = function (nr) { var number = 0; for (var i = 0; i < this.neuroConnSL.length; i++) { if (this.neuroConnSL[i].getDestination() == nr) number++; } return number; } SmartLayout.prototype.getLink = function (destination, number) { var temp = 0; for (var i = 0; i < this.neuroConnSL.length; i++) { if (this.neuroConnSL[i].getDestination() == destination) { if (temp == number) return this.neuroConnSL[i].getSource(); else temp++; } } }