diff --git a/src/kiri/client.js b/src/kiri/client.js index 15bbaf44..74deea29 100644 --- a/src/kiri/client.js +++ b/src/kiri/client.js @@ -145,6 +145,10 @@ KIRI.work = { send("snap", data, function(reply) { }); }, + png: function(data, ondone) { + send("png", data, ondone); + }, + // widget sync sync: function(widgets) { if (!widgets) { diff --git a/src/kiri/export.js b/src/kiri/export.js index 27f299ca..3d993562 100644 --- a/src/kiri/export.js +++ b/src/kiri/export.js @@ -106,10 +106,6 @@ console.log/** Copyright Stewart Allen -- All Rights Reserved */ $('print-filename').value + ".gcode"); } - function download_palette() { - console.log('todo'); - } - API.ajax("/kiri/output-laser.html", function(html) { let segments = 0; data.forEach(layer => { segments += layer.length }); @@ -465,14 +461,16 @@ console.log/** Copyright Stewart Allen -- All Rights Reserved */ if (info.segments) { // todo: reduce segments to eliminate 0 lenghts and transitions before 150mm let { settings, segments } = info; - let { bounds } = settings; + let { device, bounds } = settings; let { min, max } = bounds; let driveInfo = {}; let volume = {}; let length = {}; + // add 600mm of filament to the last segment for bowden drives + segments.peek().emitted += 650; for (let seg of segments) { let seginfo = driveInfo[seg.tool] = driveInfo[seg.tool] || { length: 0, volume: 0 }; - seginfo.length += seg.emitted; + seginfo.length += seg.emitted + 5; seginfo.volume += seg.emitted * Math.PI; volume[seg.tool+1] = seginfo.volume; length[seg.tool+1] = seginfo.length; @@ -482,7 +480,7 @@ console.log/** Copyright Stewart Allen -- All Rights Reserved */ version: "3.2", printerProfile: { id: settings.extras.palette.printer, - name: "my printer" + name: device.deviceName || "My Printer" }, preheatTemperature: { nozzle: [0], bed: 0 }, paletteNozzle: 0, @@ -536,16 +534,20 @@ console.log/** Copyright Stewart Allen -- All Rights Reserved */ pings: [], algorithms }; - console.log({meta, palette}); + let png; + KIRI.work.png({}, data => { + png = data.png; + }); downloadPalette.onclick = function() { KIRI.client.zip([ {name:"meta.json", data:JSON.stringify(meta,undefined,4)}, - {name:"palette.json", data:JSON.stringify(palette,undefined,4)} + {name:"palette.json", data:JSON.stringify(palette,undefined,4)}, + {name:"thumbnail.png", data:png.buffer} ], progress => { API.show.progress(progress.percent/100, "generating palette files"); }, output => { API.show.progress(0); - API.util.download(output, `${name}.mafx`); + API.util.download(output, `${$('print-filename').value}.mafx`); }) }; } diff --git a/src/kiri/init.js b/src/kiri/init.js index bfd13a89..e935d2bf 100644 --- a/src/kiri/init.js +++ b/src/kiri/init.js @@ -132,7 +132,7 @@ if (!conf.palette) { conf.palette = { printer: "uuid" }; } - let uuid = prompt('Printer UID from Canvas', conf.palette.printer); + let uuid = prompt('Unique Printer Identifier (can me made up)', conf.palette.printer); if (uuid) { conf.palette.printer = uuid; } diff --git a/src/kiri/main.js b/src/kiri/main.js index c0f31699..63ac73d5 100644 --- a/src/kiri/main.js +++ b/src/kiri/main.js @@ -1094,7 +1094,6 @@ if (MODE === MODES.SLA && !callback) { callback = preparePreview; } - // force layout in belt mode when widget exceeds bed length if (WIDGETS.length && settings.device.bedBelt) { let doLayout = false; diff --git a/src/kiri/worker.js b/src/kiri/worker.js index 9f0a7981..7973dfc7 100644 --- a/src/kiri/worker.js +++ b/src/kiri/worker.js @@ -218,6 +218,20 @@ KIRI.worker = { send.done(); }, + png: function(data, send) { + if (current.snap) { + let sws = current.snap.url; + let b64 = atob(sws.substring(sws.indexOf(',') + 1)); + let bin = Uint8Array.from(b64, c => c.charCodeAt(0)); + let img = new png.PNG(); + img.parse(bin, (err, data) => { + send.done({png: bin}, [ bin ]); + }); + } else { + send.done({error: "missing snapshot"}); + } + }, + clear: function(data, send) { current.snap = null; current.print = null; diff --git a/src/mode/fdm/export.js b/src/mode/fdm/export.js index db5847b1..cbda6e42 100644 --- a/src/mode/fdm/export.js +++ b/src/mode/fdm/export.js @@ -268,11 +268,16 @@ } }); } - if (extrudeAbs && line.indexOf('E') > 0) { + if (line.indexOf('E') > 0) { line.split(";")[0].split(' ').forEach(function (tok) { // use max E position from gcode-preamble if (tok[0] == 'E') { - outputLength = Math.max(outputLength, parseFloat(tok.substring(1)) || 0); + if (extrudeAbs) { + outputLength = Math.max(outputLength, parseFloat(tok.substring(1)) || 0); + emitted = outputLength; + } else { + emitted += parseFloat(tok.substring(1) || 0); + } } }); } diff --git a/src/mode/fdm/prepare.js b/src/mode/fdm/prepare.js index 209b5310..b90aaefc 100644 --- a/src/mode/fdm/prepare.js +++ b/src/mode/fdm/prepare.js @@ -243,17 +243,23 @@ } // determine size/location of purge blocks + let blokw = isPalette ? 20 : 10, blokh = isPalette ? 20 : 10; + let stepw = blokw + nozzle / 2; let blokpos, walkpos, blok; + if (bounds.min.x < bounds.min.y) { - let dx = ((bounds.max.x - bounds.min.x) - (extcount * 10)) / 2 + 5; - blokpos = { x:bounds.min.x + dx, y: bounds.max.y + 5}; - walkpos = { x:10, y:0 }; - blok = { x:9, y:4 }; + let mx = (bounds.max.x + bounds.min.x) / 2; + let px = mx - (extcount * blokw) / 2 + (blokw / 2); + let dx = ((bounds.max.x - bounds.min.x) - (extcount * blokw)) / 2; + blokpos = { x:px, y: bounds.max.y + 2 + blokh / 2}; + walkpos = { x:stepw, y:0 }; + blok = { x:blokw, y:blokh }; } else { - let dy = ((bounds.max.y - bounds.min.y) - (extcount * 10)) / 2 + 5; - blokpos = { x:bounds.max.x + 5, y: bounds.min.y + dy}; - walkpos = { x:0, y:10 }; - blok = { x:4, y:9 }; + let my = (bounds.max.y + bounds.min.y) / 2; + let py = my - (extcount * blokw) / 2 + (blokw / 2); + blokpos = { x:bounds.max.x + 2 + blokh / 2, y:py}; + walkpos = { x:0, y:stepw }; + blok = { x:blokh, y:blokw }; } // replace extruders array with object array containing more info @@ -261,30 +267,70 @@ if (!ext) return ext; let noz = device.extruders[i].extNozzle, pos = {x:blokpos.x, y:blokpos.y, z:0}, + rect = newPolygon().centerRectangle(pos, blok.x, blok.y), + full = linesToPoly(POLY.fillArea([ + newPolygon().centerRectangle(pos, blok.x - noz, blok.y - noz) + ], 45, noz)), + sparse = linesToPoly(POLY.fillArea([ + newPolygon().centerRectangle(pos, blok.x - noz, blok.y - noz) + ], 135, noz * 5)), rec = { extruder: i, - poly: newPolygon().centerSpiral(pos, blok.x, blok.y, noz*2, 3) + rect, + full, + sparse }; blokpos.x += walkpos.x; blokpos.y += walkpos.y; return rec; }); + function linesToPoly(points) { + let poly = newPolygon().setOpen(); + let ping = 0; + for (let i=0; i= 0 || lastPurgeTool === nozzle; + let tool = using >= 0 ? using : nozzle; + let first = layer.slice.index === 0; + let rate = first ? process.firstLayerRate : process.outputFeedrate; + lastPurgeTool = tool; if (rec) { track[nozzle] = null; if (layer.last()) { layer.last().retract = true; } - start = print.polyPrintPath(rec.poly.clone().setZ(z), start, layer, { - tool: using !== undefined ? using : nozzle, + start = print.polyPrintPath(rec.rect.clone().setZ(z), start, layer, { + tool, + rate, + simple: true, + open: false, + }); + start = print.polyPrintPath((thin && !first ? rec.sparse : rec.full).clone().setZ(z), start, layer, { + tool, + rate, + simple: true, open: true, - simple: true }); layer.last().retract = true; return start;