Merge remote-tracking branch 'remotes/prusa/et_custom_bed'

sorry, forgot to commit it before doing changes.
so there are also the bug fix for #76 and #74
This commit is contained in:
supermerill 2019-07-03 20:47:31 +02:00
commit 6b20a930eb
71 changed files with 1355 additions and 801 deletions

9
deps/CMakeLists.txt vendored
View File

@ -36,10 +36,11 @@ set(DESTDIR "${CMAKE_CURRENT_BINARY_DIR}/destdir" CACHE PATH "Destination direct
option(DEP_DEBUG "Build debug variants (only applicable on Windows)" ON) option(DEP_DEBUG "Build debug variants (only applicable on Windows)" ON)
option(DEP_WX_STABLE "Build against wxWidgets stable 3.0 as opposed to default 3.1 (Linux only)" OFF) option(DEP_WX_STABLE "Build against wxWidgets stable 3.0 as opposed to default 3.1 (Linux only)" OFF)
# IGL static library in release mode produces 50MB binary. On the build server, it should be # On developer machines, it can be enabled to speed up compilation and suppress warnings coming from IGL.
# disabled and used in header-only mode. On developer machines, it can be enabled to speed # FIXME:
# up conpilation and suppress warnings coming from IGL. # Enabling this option is not safe. IGL will compile itself with its own version of Eigen while
option(DEP_BUILD_IGL_STATIC "Build IGL as a static library. Might cause link errors and increase binary size." OFF) # Slic3r compiles with a different version which will cause runtime errors.
# option(DEP_BUILD_IGL_STATIC "Build IGL as a static library. Might cause link errors and increase binary size." OFF)
message(STATUS "Slic3r deps DESTDIR: ${DESTDIR}") message(STATUS "Slic3r deps DESTDIR: ${DESTDIR}")
message(STATUS "Slic3r deps debug build: ${DEP_DEBUG}") message(STATUS "Slic3r deps debug build: ${DEP_DEBUG}")

View File

@ -54,7 +54,7 @@ ExternalProject_Add(dep_libigl
-DLIBIGL_BUILD_PYTHON=OFF -DLIBIGL_BUILD_PYTHON=OFF
-DLIBIGL_BUILD_TESTS=OFF -DLIBIGL_BUILD_TESTS=OFF
-DLIBIGL_BUILD_TUTORIALS=OFF -DLIBIGL_BUILD_TUTORIALS=OFF
-DLIBIGL_USE_STATIC_LIBRARY=${DEP_BUILD_IGL_STATIC} -DLIBIGL_USE_STATIC_LIBRARY=OFF #${DEP_BUILD_IGL_STATIC}
-DLIBIGL_WITHOUT_COPYLEFT=OFF -DLIBIGL_WITHOUT_COPYLEFT=OFF
-DLIBIGL_WITH_CGAL=OFF -DLIBIGL_WITH_CGAL=OFF
-DLIBIGL_WITH_COMISO=OFF -DLIBIGL_WITH_COMISO=OFF

View File

@ -273,7 +273,7 @@ ExternalProject_Add(dep_libigl
-DLIBIGL_BUILD_PYTHON=OFF -DLIBIGL_BUILD_PYTHON=OFF
-DLIBIGL_BUILD_TESTS=OFF -DLIBIGL_BUILD_TESTS=OFF
-DLIBIGL_BUILD_TUTORIALS=OFF -DLIBIGL_BUILD_TUTORIALS=OFF
-DLIBIGL_USE_STATIC_LIBRARY=${DEP_BUILD_IGL_STATIC} -DLIBIGL_USE_STATIC_LIBRARY=OFF #${DEP_BUILD_IGL_STATIC}
-DLIBIGL_WITHOUT_COPYLEFT=OFF -DLIBIGL_WITHOUT_COPYLEFT=OFF
-DLIBIGL_WITH_CGAL=OFF -DLIBIGL_WITH_CGAL=OFF
-DLIBIGL_WITH_COMISO=OFF -DLIBIGL_WITH_COMISO=OFF

View File

@ -579,7 +579,7 @@ void CLI::print_help(bool include_print_options, PrinterTechnology printer_techn
#endif /* SLIC3R_GUI */ #endif /* SLIC3R_GUI */
<< std::endl << std::endl
<< "https://github.com/supermerill/slic3r" << std::endl << std::endl << "https://github.com/supermerill/slic3r" << std::endl << std::endl
<< "Usage: slic3r [ ACTIONS ] [ TRANSFORM ] [ OPTIONS ] [ file.stl ... ]" << std::endl << "Usage: prusa-slicer [ ACTIONS ] [ TRANSFORM ] [ OPTIONS ] [ file.stl ... ]" << std::endl
<< std::endl << std::endl
<< "Actions:" << std::endl; << "Actions:" << std::endl;
cli_actions_config_def.print_cli_help(boost::nowide::cout, false); cli_actions_config_def.print_cli_help(boost::nowide::cout, false);

View File

@ -41,6 +41,7 @@
static int arduino_read_sig_bytes(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m) static int arduino_read_sig_bytes(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m)
{ {
unsigned char buf[32]; unsigned char buf[32];
(void)p;
/* Signature byte reads are always 3 bytes. */ /* Signature byte reads are always 3 bytes. */
@ -83,9 +84,9 @@ static int arduino_read_sig_bytes(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m)
static int prusa_init_external_flash(PROGRAMMER * pgm) static int prusa_init_external_flash(PROGRAMMER * pgm)
{ {
// Note: send/receive as in _the firmare_ send & receives // Note: send/receive as in _the firmare_ send & receives
const char entry_magic_send [] = "start\n"; const char entry_magic_send[] = "start\n";
const char entry_magic_receive[] = "w25x20cl_enter\n"; const unsigned char entry_magic_receive[] = "w25x20cl_enter\n";
const char entry_magic_cfm [] = "w25x20cl_cfm\n"; const char entry_magic_cfm[] = "w25x20cl_cfm\n";
const size_t buffer_len = 32; // Should be large enough for the above messages const size_t buffer_len = 32; // Should be large enough for the above messages
int res; int res;
@ -94,7 +95,7 @@ static int prusa_init_external_flash(PROGRAMMER * pgm)
// 1. receive the "start" command // 1. receive the "start" command
recv_size = sizeof(entry_magic_send) - 1; recv_size = sizeof(entry_magic_send) - 1;
res = serial_recv(&pgm->fd, buffer, recv_size); res = serial_recv(&pgm->fd, (unsigned char *)buffer, recv_size);
if (res < 0) { if (res < 0) {
avrdude_message(MSG_INFO, "%s: prusa_init_external_flash(): MK3 printer did not boot up on time or serial communication failed\n", progname); avrdude_message(MSG_INFO, "%s: prusa_init_external_flash(): MK3 printer did not boot up on time or serial communication failed\n", progname);
return -1; return -1;
@ -111,7 +112,7 @@ static int prusa_init_external_flash(PROGRAMMER * pgm)
// 3. Receive the entry confirmation command // 3. Receive the entry confirmation command
recv_size = sizeof(entry_magic_cfm) - 1; recv_size = sizeof(entry_magic_cfm) - 1;
res = serial_recv(&pgm->fd, buffer, recv_size); res = serial_recv(&pgm->fd, (unsigned char *)buffer, recv_size);
if (res < 0) { if (res < 0) {
avrdude_message(MSG_INFO, "%s: prusa_init_external_flash(): MK3 printer did not boot up on time or serial communication failed\n", progname); avrdude_message(MSG_INFO, "%s: prusa_init_external_flash(): MK3 printer did not boot up on time or serial communication failed\n", progname);
return -1; return -1;
@ -142,7 +143,7 @@ static int arduino_open(PROGRAMMER * pgm, char * port)
// Sometimes there may be line noise generating input on the printer's USB-to-serial IC // Sometimes there may be line noise generating input on the printer's USB-to-serial IC
// Here we try to clean its input buffer with a sequence of newlines (a minimum of 9 is needed): // Here we try to clean its input buffer with a sequence of newlines (a minimum of 9 is needed):
const char cleanup_newlines[] = "\n\n\n\n\n\n\n\n\n\n"; const unsigned char cleanup_newlines[] = "\n\n\n\n\n\n\n\n\n\n";
if (serial_send(&pgm->fd, cleanup_newlines, sizeof(cleanup_newlines) - 1) < 0) { if (serial_send(&pgm->fd, cleanup_newlines, sizeof(cleanup_newlines) - 1) < 0) {
return -1; return -1;
} }

View File

@ -341,7 +341,7 @@ int avr_read(PROGRAMMER * pgm, AVRPART * p, char * memtype,
avr_tpi_setup_rw(pgm, mem, 0, TPI_NVMCMD_NO_OPERATION); avr_tpi_setup_rw(pgm, mem, 0, TPI_NVMCMD_NO_OPERATION);
/* load bytes */ /* load bytes */
for (lastaddr = i = 0; i < mem->size; i++) { for (lastaddr = i = 0; i < (unsigned)mem->size; i++) {
RETURN_IF_CANCEL(); RETURN_IF_CANCEL();
if (vmem == NULL || if (vmem == NULL ||
(vmem->tags[i] & TAG_ALLOCATED) != 0) (vmem->tags[i] & TAG_ALLOCATED) != 0)
@ -374,7 +374,7 @@ int avr_read(PROGRAMMER * pgm, AVRPART * p, char * memtype,
/* quickly scan number of pages to be written to first */ /* quickly scan number of pages to be written to first */
for (pageaddr = 0, npages = 0; for (pageaddr = 0, npages = 0;
pageaddr < mem->size; pageaddr < (unsigned)mem->size;
pageaddr += mem->page_size) { pageaddr += mem->page_size) {
/* check whether this page must be read */ /* check whether this page must be read */
for (i = pageaddr; for (i = pageaddr;
@ -391,7 +391,7 @@ int avr_read(PROGRAMMER * pgm, AVRPART * p, char * memtype,
} }
for (pageaddr = 0, failure = 0, nread = 0; for (pageaddr = 0, failure = 0, nread = 0;
!failure && pageaddr < mem->size; !failure && pageaddr < (unsigned)mem->size;
pageaddr += mem->page_size) { pageaddr += mem->page_size) {
RETURN_IF_CANCEL(); RETURN_IF_CANCEL();
/* check whether this page must be read */ /* check whether this page must be read */
@ -437,7 +437,7 @@ int avr_read(PROGRAMMER * pgm, AVRPART * p, char * memtype,
} }
} }
for (i=0; i < mem->size; i++) { for (i = 0; i < (unsigned)mem->size; i++) {
RETURN_IF_CANCEL(); RETURN_IF_CANCEL();
if (vmem == NULL || if (vmem == NULL ||
(vmem->tags[i] & TAG_ALLOCATED) != 0) (vmem->tags[i] & TAG_ALLOCATED) != 0)
@ -634,18 +634,18 @@ int avr_write_byte_default(PROGRAMMER * pgm, AVRPART * p, AVRMEM * mem,
writeop = mem->op[AVR_OP_WRITE_HI]; writeop = mem->op[AVR_OP_WRITE_HI];
else else
writeop = mem->op[AVR_OP_WRITE_LO]; writeop = mem->op[AVR_OP_WRITE_LO];
caddr = addr / 2; caddr = (unsigned short)(addr / 2);
} }
else if (mem->paged && mem->op[AVR_OP_LOADPAGE_LO]) { else if (mem->paged && mem->op[AVR_OP_LOADPAGE_LO]) {
if (addr & 0x01) if (addr & 0x01)
writeop = mem->op[AVR_OP_LOADPAGE_HI]; writeop = mem->op[AVR_OP_LOADPAGE_HI];
else else
writeop = mem->op[AVR_OP_LOADPAGE_LO]; writeop = mem->op[AVR_OP_LOADPAGE_LO];
caddr = addr / 2; caddr = (unsigned short)(addr / 2);
} }
else { else {
writeop = mem->op[AVR_OP_WRITE]; writeop = mem->op[AVR_OP_WRITE];
caddr = addr; caddr = (unsigned short)addr;
} }
if (writeop == NULL) { if (writeop == NULL) {
@ -723,7 +723,7 @@ int avr_write_byte_default(PROGRAMMER * pgm, AVRPART * p, AVRMEM * mem,
gettimeofday (&tv, NULL); gettimeofday (&tv, NULL);
prog_time = (tv.tv_sec * 1000000) + tv.tv_usec; prog_time = (tv.tv_sec * 1000000) + tv.tv_usec;
} while ((r != data) && } while ((r != data) &&
((prog_time-start_time) < mem->max_write_delay)); ((prog_time - start_time) < (unsigned long)mem->max_write_delay));
} }
/* /*
@ -878,7 +878,7 @@ int avr_write(PROGRAMMER * pgm, AVRPART * p, char * memtype, int size,
} }
/* write words, low byte first */ /* write words, low byte first */
for (lastaddr = i = 0; i < wsize; i += 2) { for (lastaddr = i = 0; i < (unsigned)wsize; i += 2) {
RETURN_IF_CANCEL(); RETURN_IF_CANCEL();
if ((m->tags[i] & TAG_ALLOCATED) != 0 || if ((m->tags[i] & TAG_ALLOCATED) != 0 ||
(m->tags[i + 1] & TAG_ALLOCATED) != 0) { (m->tags[i + 1] & TAG_ALLOCATED) != 0) {
@ -915,7 +915,7 @@ int avr_write(PROGRAMMER * pgm, AVRPART * p, char * memtype, int size,
/* quickly scan number of pages to be written to first */ /* quickly scan number of pages to be written to first */
for (pageaddr = 0, npages = 0; for (pageaddr = 0, npages = 0;
pageaddr < wsize; pageaddr < (unsigned)wsize;
pageaddr += m->page_size) { pageaddr += m->page_size) {
/* check whether this page must be written to */ /* check whether this page must be written to */
for (i = pageaddr; for (i = pageaddr;
@ -928,7 +928,7 @@ int avr_write(PROGRAMMER * pgm, AVRPART * p, char * memtype, int size,
} }
for (pageaddr = 0, failure = 0, nwritten = 0; for (pageaddr = 0, failure = 0, nwritten = 0;
!failure && pageaddr < wsize; !failure && pageaddr < (unsigned)wsize;
pageaddr += m->page_size) { pageaddr += m->page_size) {
RETURN_IF_CANCEL(); RETURN_IF_CANCEL();
/* check whether this page must be written to */ /* check whether this page must be written to */
@ -968,7 +968,7 @@ int avr_write(PROGRAMMER * pgm, AVRPART * p, char * memtype, int size,
page_tainted = 0; page_tainted = 0;
flush_page = 0; flush_page = 0;
for (i=0; i<wsize; i++) { for (i = 0; i < (unsigned)wsize; i++) {
RETURN_IF_CANCEL(); RETURN_IF_CANCEL();
data = m->buf[i]; data = m->buf[i];
report_progress(i, wsize, NULL); report_progress(i, wsize, NULL);

View File

@ -676,7 +676,7 @@ static int avr910_paged_load(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m,
avr910_set_addr(pgm, addr / rd_size); avr910_set_addr(pgm, addr / rd_size);
while (addr < max_addr) { while (addr < max_addr) {
if ((max_addr - addr) < blocksize) { if ((max_addr - addr) < (unsigned)blocksize) {
blocksize = max_addr - addr; blocksize = max_addr - addr;
} }
cmd[1] = (blocksize >> 8) & 0xff; cmd[1] = (blocksize >> 8) & 0xff;

View File

@ -1,5 +1,5 @@
/* WARN: This file is auto-generated from `avrdude-slic3r.conf` */ /* WARN: This file is auto-generated from `avrdude-slic3r.conf` */
unsigned char avrdude_slic3r_conf[] = { const unsigned char avrdude_slic3r_conf[] = {
0x0a, 0x23, 0x0a, 0x23, 0x20, 0x54, 0x68, 0x69, 0x73, 0x20, 0x69, 0x73, 0x0a, 0x23, 0x0a, 0x23, 0x20, 0x54, 0x68, 0x69, 0x73, 0x20, 0x69, 0x73,
0x20, 0x61, 0x20, 0x62, 0x61, 0x73, 0x69, 0x63, 0x20, 0x6d, 0x69, 0x6e, 0x20, 0x61, 0x20, 0x62, 0x61, 0x73, 0x69, 0x63, 0x20, 0x6d, 0x69, 0x6e,
0x69, 0x6d, 0x61, 0x6c, 0x20, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x20, 0x69, 0x6d, 0x61, 0x6c, 0x20, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x20,
@ -1184,5 +1184,5 @@ unsigned char avrdude_slic3r_conf[] = {
0x20, 0x20, 0x3b, 0x0a, 0x0a, 0x0a, 0x20, 0x20, 0x3b, 0x0a, 0x0a, 0x0a,
0, 0 0, 0
}; };
size_t avrdude_slic3r_conf_size = 14178; const size_t avrdude_slic3r_conf_size = 14178;
size_t avrdude_slic3r_conf_size_yy = 14180; const size_t avrdude_slic3r_conf_size_yy = 14180;

View File

@ -93,7 +93,7 @@ void AvrDude::priv::unset_handlers()
int AvrDude::priv::run_one(const std::vector<std::string> &args) { int AvrDude::priv::run_one(const std::vector<std::string> &args) {
std::vector<char*> c_args {{ const_cast<char*>(PACKAGE) }}; std::vector<char*> c_args { const_cast<char*>(PACKAGE) };
std::string command_line { PACKAGE }; std::string command_line { PACKAGE };
for (const auto &arg : args) { for (const auto &arg : args) {
@ -105,7 +105,7 @@ int AvrDude::priv::run_one(const std::vector<std::string> &args) {
HandlerGuard guard(*this); HandlerGuard guard(*this);
message_fn(command_line.c_str(), command_line.size()); message_fn(command_line.c_str(), (unsigned)command_line.size());
const auto res = ::avrdude_main(static_cast<int>(c_args.size()), c_args.data()); const auto res = ::avrdude_main(static_cast<int>(c_args.size()), c_args.data());
@ -200,7 +200,7 @@ AvrDude::Ptr AvrDude::run()
auto &message_fn = self->p->message_fn; auto &message_fn = self->p->message_fn;
if (message_fn) { if (message_fn) {
message_fn(msg, sizeof(msg)); message_fn(msg, sizeof(msg));
message_fn(what, std::strlen(what)); message_fn(what, (unsigned)std::strlen(what));
message_fn("\n", 1); message_fn("\n", 1);
} }

View File

@ -64,6 +64,8 @@ int avrdude_main(int argc, char * argv []);
#include <windows.h> #include <windows.h>
#include <unistd.h> #include <unistd.h>
#define strdup _strdup
#ifdef UNICODE #ifdef UNICODE
#error "UNICODE should not be defined for avrdude bits on Windows" #error "UNICODE should not be defined for avrdude bits on Windows"
#endif #endif

View File

@ -358,7 +358,7 @@ AVRMEM * avr_locate_mem(AVRPART * p, char * desc)
int matches; int matches;
int l; int l;
l = strlen(desc); l = (int)strlen(desc);
matches = 0; matches = 0;
match = NULL; match = NULL;
for (ln=lfirst(p->mem); ln; ln=lnext(ln)) { for (ln=lfirst(p->mem); ln; ln=lnext(ln)) {
@ -662,7 +662,7 @@ void avr_display(FILE * f, AVRPART * p, const char * prefix, int verbose)
prefix); prefix);
px = prefix; px = prefix;
i = strlen(prefix) + 5; i = (int)strlen(prefix) + 5;
buf = (char *)malloc(i); buf = (char *)malloc(i);
if (buf == NULL) { if (buf == NULL) {
/* ugh, this is not important enough to bail, just ignore it */ /* ugh, this is not important enough to bail, just ignore it */

View File

@ -128,7 +128,7 @@ static int buspirate_recv_bin(struct programmer_t *pgm, unsigned char *buf, size
avrdude_message(MSG_DEBUG, "%s: buspirate_recv_bin():\n", progname); avrdude_message(MSG_DEBUG, "%s: buspirate_recv_bin():\n", progname);
dump_mem(MSG_DEBUG, buf, len); dump_mem(MSG_DEBUG, buf, len);
return len; return (int)len;
} }
static int buspirate_expect_bin(struct programmer_t *pgm, static int buspirate_expect_bin(struct programmer_t *pgm,
@ -249,7 +249,7 @@ static int buspirate_send(struct programmer_t *pgm, const char *str)
static int buspirate_is_prompt(const char *str) static int buspirate_is_prompt(const char *str)
{ {
int strlen_str = strlen(str); int strlen_str = (int)strlen(str);
/* Prompt ends with '>' or '> ' /* Prompt ends with '>' or '> '
* all other input probably ends with '\n' */ * all other input probably ends with '\n' */
return (str[strlen_str - 1] == '>' || str[strlen_str - 2] == '>'); return (str[strlen_str - 1] == '>' || str[strlen_str - 2] == '>');

View File

@ -675,7 +675,7 @@ static int butterfly_paged_load(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m,
butterfly_set_addr(pgm, addr / rd_size); butterfly_set_addr(pgm, addr / rd_size);
} }
while (addr < max_addr) { while (addr < max_addr) {
if ((max_addr - addr) < blocksize) { if ((max_addr - addr) < (unsigned)blocksize) {
blocksize = max_addr - addr; blocksize = max_addr - addr;
}; };
cmd[1] = (blocksize >> 8) & 0xff; cmd[1] = (blocksize >> 8) & 0xff;

View File

@ -21,7 +21,7 @@ int main(int argc, char const *argv[])
} }
std::cout << "/* WARN: This file is auto-generated from `" << filename << "` */" << std::endl; std::cout << "/* WARN: This file is auto-generated from `" << filename << "` */" << std::endl;
std::cout << "unsigned char " << symbol << "[] = {"; std::cout << "const unsigned char " << symbol << "[] = {";
char c; char c;
std::cout << std::hex; std::cout << std::hex;
@ -34,8 +34,8 @@ int main(int argc, char const *argv[])
std::cout << "\n 0, 0\n};\n"; std::cout << "\n 0, 0\n};\n";
std::cout << std::dec; std::cout << std::dec;
std::cout << "size_t " << symbol << "_size = " << size << ";" << std::endl; std::cout << "const size_t " << symbol << "_size = " << size << ";" << std::endl;
std::cout << "size_t " << symbol << "_size_yy = " << size + 2 << ";" << std::endl; std::cout << "const size_t " << symbol << "_size_yy = " << size + 2 << ";" << std::endl;
return 0; return 0;
} }

View File

@ -240,7 +240,7 @@ TOKEN * string(char * text)
return NULL; /* yyerror already called */ return NULL; /* yyerror already called */
} }
len = strlen(text); len = (int)strlen(text);
tkn->value.type = V_STR; tkn->value.type = V_STR;
tkn->value.string = (char *) malloc(len+1); tkn->value.string = (char *) malloc(len+1);
@ -351,7 +351,7 @@ int read_config(const char * file)
} }
typedef struct yy_buffer_state *YY_BUFFER_STATE; typedef struct yy_buffer_state *YY_BUFFER_STATE;
extern YY_BUFFER_STATE yy_scan_bytes(char *base, size_t size); extern YY_BUFFER_STATE yy_scan_bytes(const char *base, size_t size);
extern void yy_delete_buffer(YY_BUFFER_STATE b); extern void yy_delete_buffer(YY_BUFFER_STATE b);
int read_config_builtin() int read_config_builtin()
@ -363,7 +363,7 @@ int read_config_builtin()
// Note: Can't use yy_scan_buffer, it's buggy (?), leads to fread from a null FILE* // Note: Can't use yy_scan_buffer, it's buggy (?), leads to fread from a null FILE*
// and so unfortunatelly we have to use the copying variant here // and so unfortunatelly we have to use the copying variant here
YY_BUFFER_STATE buffer = yy_scan_bytes(avrdude_slic3r_conf, avrdude_slic3r_conf_size); YY_BUFFER_STATE buffer = yy_scan_bytes((const char *)avrdude_slic3r_conf, avrdude_slic3r_conf_size);
if (buffer == NULL) { if (buffer == NULL) {
avrdude_message(MSG_INFO, "%s: read_config_builtin: Failed to initialize parsing buffer\n", progname); avrdude_message(MSG_INFO, "%s: read_config_builtin: Failed to initialize parsing buffer\n", progname);
return -1; return -1;

View File

@ -3640,7 +3640,7 @@ static int parse_cmdbits(OPCODE * op)
break; break;
} }
len = strlen(s); len = (int)strlen(s);
if (len == 0) { if (len == 0) {
yyerror("invalid bit specifier \"\""); yyerror("invalid bit specifier \"\"");

View File

@ -1493,7 +1493,7 @@ static int parse_cmdbits(OPCODE * op)
break; break;
} }
len = strlen(s); len = (int)strlen(s);
if (len == 0) { if (len == 0) {
yyerror("invalid bit specifier \"\""); yyerror("invalid bit specifier \"\"");

View File

@ -264,7 +264,7 @@ static int ihex_readrec(struct ihexrec * ihex, char * rec)
unsigned char cksum; unsigned char cksum;
int rc; int rc;
len = strlen(rec); len = (int)strlen(rec);
offset = 1; offset = 1;
cksum = 0; cksum = 0;
@ -274,7 +274,7 @@ static int ihex_readrec(struct ihexrec * ihex, char * rec)
for (i=0; i<2; i++) for (i=0; i<2; i++)
buf[i] = rec[offset++]; buf[i] = rec[offset++];
buf[i] = 0; buf[i] = 0;
ihex->reclen = strtoul(buf, &e, 16); ihex->reclen = (unsigned char)strtoul(buf, &e, 16);
if (e == buf || *e != 0) if (e == buf || *e != 0)
return -1; return -1;
@ -294,7 +294,7 @@ static int ihex_readrec(struct ihexrec * ihex, char * rec)
for (i=0; i<2; i++) for (i=0; i<2; i++)
buf[i] = rec[offset++]; buf[i] = rec[offset++];
buf[i] = 0; buf[i] = 0;
ihex->rectyp = strtoul(buf, &e, 16); ihex->rectyp = (unsigned char)strtoul(buf, &e, 16);
if (e == buf || *e != 0) if (e == buf || *e != 0)
return -1; return -1;
@ -308,7 +308,7 @@ static int ihex_readrec(struct ihexrec * ihex, char * rec)
for (i=0; i<2; i++) for (i=0; i<2; i++)
buf[i] = rec[offset++]; buf[i] = rec[offset++];
buf[i] = 0; buf[i] = 0;
ihex->data[j] = strtoul(buf, &e, 16); ihex->data[j] = (char)strtoul(buf, &e, 16);
if (e == buf || *e != 0) if (e == buf || *e != 0)
return -1; return -1;
cksum += ihex->data[j]; cksum += ihex->data[j];
@ -320,7 +320,7 @@ static int ihex_readrec(struct ihexrec * ihex, char * rec)
for (i=0; i<2; i++) for (i=0; i<2; i++)
buf[i] = rec[offset++]; buf[i] = rec[offset++];
buf[i] = 0; buf[i] = 0;
ihex->cksum = strtoul(buf, &e, 16); ihex->cksum = (char)strtoul(buf, &e, 16);
if (e == buf || *e != 0) if (e == buf || *e != 0)
return -1; return -1;
@ -361,7 +361,7 @@ static int ihex2b(char * infile, FILE * inf,
while (fgets((char *)buffer,MAX_LINE_LEN,inf)!=NULL) { while (fgets((char *)buffer,MAX_LINE_LEN,inf)!=NULL) {
lineno++; lineno++;
len = strlen(buffer); len = (int)strlen(buffer);
if (buffer[len-1] == '\n') if (buffer[len-1] == '\n')
buffer[--len] = 0; buffer[--len] = 0;
if (buffer[0] != ':') if (buffer[0] != ':')
@ -388,7 +388,7 @@ static int ihex2b(char * infile, FILE * inf,
return -1; return -1;
} }
nextaddr = ihex.loadofs + baseaddr - fileoffset; nextaddr = ihex.loadofs + baseaddr - fileoffset;
if (nextaddr + ihex.reclen > bufsize) { if (nextaddr + ihex.reclen > (unsigned)bufsize) {
avrdude_message(MSG_INFO, "%s: ERROR: address 0x%04x out of range at line %d of %s\n", avrdude_message(MSG_INFO, "%s: ERROR: address 0x%04x out of range at line %d of %s\n",
progname, nextaddr+ihex.reclen, lineno, infile); progname, nextaddr+ihex.reclen, lineno, infile);
return -1; return -1;
@ -502,10 +502,11 @@ static int b2srec(unsigned char * inbuf, int bufsize,
cksum += n + addr_width + 1; cksum += n + addr_width + 1;
for (i=addr_width; i>0; i--) for (i = addr_width; i>0; i--) {
cksum += (nextaddr >> (i-1) * 8) & 0xff; cksum += (nextaddr >> (i-1) * 8) & 0xff;
}
for (i=nextaddr; i<nextaddr + n; i++) { for (unsigned i = nextaddr; i < nextaddr + n; i++) {
fprintf(outf, "%02X", buf[i]); fprintf(outf, "%02X", buf[i]);
cksum += buf[i]; cksum += buf[i];
} }
@ -562,7 +563,7 @@ static int srec_readrec(struct ihexrec * srec, char * rec)
unsigned char cksum; unsigned char cksum;
int rc; int rc;
len = strlen(rec); len = (int)strlen(rec);
offset = 1; offset = 1;
cksum = 0; cksum = 0;
addr_width = 2; addr_width = 2;
@ -582,7 +583,7 @@ static int srec_readrec(struct ihexrec * srec, char * rec)
for (i=0; i<2; i++) for (i=0; i<2; i++)
buf[i] = rec[offset++]; buf[i] = rec[offset++];
buf[i] = 0; buf[i] = 0;
srec->reclen = strtoul(buf, &e, 16); srec->reclen = (char)strtoul(buf, &e, 16);
cksum += srec->reclen; cksum += srec->reclen;
srec->reclen -= (addr_width+1); srec->reclen -= (addr_width+1);
if (e == buf || *e != 0) if (e == buf || *e != 0)
@ -594,7 +595,7 @@ static int srec_readrec(struct ihexrec * srec, char * rec)
for (i=0; i<addr_width*2; i++) for (i=0; i<addr_width*2; i++)
buf[i] = rec[offset++]; buf[i] = rec[offset++];
buf[i] = 0; buf[i] = 0;
srec->loadofs = strtoull(buf, &e, 16); srec->loadofs = strtoul(buf, &e, 16);
if (e == buf || *e != 0) if (e == buf || *e != 0)
return -1; return -1;
@ -608,7 +609,7 @@ static int srec_readrec(struct ihexrec * srec, char * rec)
for (i=0; i<2; i++) for (i=0; i<2; i++)
buf[i] = rec[offset++]; buf[i] = rec[offset++];
buf[i] = 0; buf[i] = 0;
srec->data[j] = strtoul(buf, &e, 16); srec->data[j] = (char)strtoul(buf, &e, 16);
if (e == buf || *e != 0) if (e == buf || *e != 0)
return -1; return -1;
cksum += srec->data[j]; cksum += srec->data[j];
@ -620,7 +621,7 @@ static int srec_readrec(struct ihexrec * srec, char * rec)
for (i=0; i<2; i++) for (i=0; i<2; i++)
buf[i] = rec[offset++]; buf[i] = rec[offset++];
buf[i] = 0; buf[i] = 0;
srec->cksum = strtoul(buf, &e, 16); srec->cksum = (char)strtoul(buf, &e, 16);
if (e == buf || *e != 0) if (e == buf || *e != 0)
return -1; return -1;
@ -650,7 +651,7 @@ static int srec2b(char * infile, FILE * inf,
while (fgets((char *)buffer,MAX_LINE_LEN,inf)!=NULL) { while (fgets((char *)buffer,MAX_LINE_LEN,inf)!=NULL) {
lineno++; lineno++;
len = strlen(buffer); len = (int)strlen(buffer);
if (buffer[len-1] == '\n') if (buffer[len-1] == '\n')
buffer[--len] = 0; buffer[--len] = 0;
if (buffer[0] != 0x53) if (buffer[0] != 0x53)
@ -729,7 +730,7 @@ static int srec2b(char * infile, FILE * inf,
return -1; return -1;
} }
nextaddr -= fileoffset; nextaddr -= fileoffset;
if (nextaddr + srec.reclen > bufsize) { if (nextaddr + srec.reclen > (unsigned)bufsize) {
avrdude_message(MSG_INFO, msg, progname, nextaddr+srec.reclen, "", avrdude_message(MSG_INFO, msg, progname, nextaddr+srec.reclen, "",
lineno, infile); lineno, infile);
return -1; return -1;
@ -1143,12 +1144,12 @@ static int fileio_rbin(struct fioparms * fio,
switch (fio->op) { switch (fio->op) {
case FIO_READ: case FIO_READ:
rc = fread(buf, 1, size, f); rc = (int)fread(buf, 1, size, f);
if (rc > 0) if (rc > 0)
memset(mem->tags, TAG_ALLOCATED, rc); memset(mem->tags, TAG_ALLOCATED, rc);
break; break;
case FIO_WRITE: case FIO_WRITE:
rc = fwrite(buf, 1, size, f); rc = (int)fwrite(buf, 1, size, f);
break; break;
default: default:
avrdude_message(MSG_INFO, "%s: fileio: invalid operation=%d\n", avrdude_message(MSG_INFO, "%s: fileio: invalid operation=%d\n",
@ -1190,7 +1191,7 @@ static int fileio_imm(struct fioparms * fio,
progname, p); progname, p);
return -1; return -1;
} }
mem->buf[loc] = b; mem->buf[loc] = (char)b;
mem->tags[loc++] = TAG_ALLOCATED; mem->tags[loc++] = TAG_ALLOCATED;
p = strtok(NULL, " ,"); p = strtok(NULL, " ,");
rc = loc; rc = loc;
@ -1452,7 +1453,7 @@ static int fmt_autodetect(char * fname, unsigned section)
} }
buf[MAX_LINE_LEN-1] = 0; buf[MAX_LINE_LEN-1] = 0;
len = strlen((char *)buf); len = (int)strlen((char *)buf);
if (buf[len-1] == '\n') if (buf[len-1] == '\n')
buf[--len] = 0; buf[--len] = 0;

View File

@ -444,7 +444,7 @@ lcreat ( void * liststruct, int elements )
l->poolsize = DEFAULT_POOLSIZE; l->poolsize = DEFAULT_POOLSIZE;
} }
else { else {
l->poolsize = elements*sizeof(LISTNODE)+sizeof(NODEPOOL); l->poolsize = (short)(elements*sizeof(LISTNODE)+sizeof(NODEPOOL));
} }
l->n_ln_pool = (l->poolsize-sizeof(NODEPOOL))/sizeof(LISTNODE); l->n_ln_pool = (l->poolsize-sizeof(NODEPOOL))/sizeof(LISTNODE);
@ -803,7 +803,7 @@ lget_n ( LISTID lid, unsigned int n )
CKLMAGIC(l); CKLMAGIC(l);
if ((n<1)||(n>lsize(l))) { if ((n < 1) || (n > (unsigned)lsize(l))) {
return NULL; return NULL;
} }
@ -844,7 +844,7 @@ lget_ln ( LISTID lid, unsigned int n )
CKLMAGIC(l); CKLMAGIC(l);
if ((n<1)||(n>lsize(l))) { if ((n < 1) || (n > (unsigned)lsize(l))) {
return NULL; return NULL;
} }
@ -952,7 +952,7 @@ lins_n ( LISTID lid, void * data_ptr, unsigned int n )
CKLMAGIC(l); CKLMAGIC(l);
if ((n<1)||(n>(l->num+1))) { if ((n < 1) || (n > (unsigned)(l->num+1))) {
return -1; return -1;
} }
@ -1193,7 +1193,7 @@ lrmv_n ( LISTID lid, unsigned int n )
CKLMAGIC(l); CKLMAGIC(l);
if ((n<1)||(n>l->num)) { if ((n < 1) || (n > (unsigned)l->num)) {
return NULL; return NULL;
} }

View File

@ -107,7 +107,7 @@ int avrdude_message(const int msglvl, const char *format, ...)
if (rc > 0 && rc < MSGBUFFER_SIZE) { if (rc > 0 && rc < MSGBUFFER_SIZE) {
avrdude_message_handler(msgbuffer, rc, avrdude_message_handler_user_p); avrdude_message_handler(msgbuffer, rc, avrdude_message_handler_user_p);
} else { } else {
avrdude_message_handler(format_error, strlen(format_error), avrdude_message_handler_user_p); avrdude_message_handler(format_error, (unsigned)strlen(format_error), avrdude_message_handler_user_p);
} }
} }
@ -567,7 +567,7 @@ int avrdude_main(int argc, char * argv [])
// #endif // #endif
len = strlen(progname) + 2; len = (int)strlen(progname) + 2;
for (i=0; i<len; i++) for (i=0; i<len; i++)
progbuf[i] = ' '; progbuf[i] = ' ';
progbuf[i] = 0; progbuf[i] = 0;
@ -601,7 +601,7 @@ int avrdude_main(int argc, char * argv [])
bitclock = strtod(optarg, &e); bitclock = strtod(optarg, &e);
if (*e != 0) { if (*e != 0) {
/* trailing unit of measure present */ /* trailing unit of measure present */
int suffixlen = strlen(e); size_t suffixlen = strlen(e);
switch (suffixlen) { switch (suffixlen) {
case 2: case 2:
if ((e[0] != 'h' && e[0] != 'H') || e[1] != 'z') if ((e[0] != 'h' && e[0] != 'H') || e[1] != 'z')

View File

@ -217,7 +217,7 @@ const char * pinmask_to_str(const pinmask_t * const pinmask) {
* @param[in] size the number of entries in checklist * @param[in] size the number of entries in checklist
* @returns 0 if all pin definitions are valid, -1 otherwise * @returns 0 if all pin definitions are valid, -1 otherwise
*/ */
int pins_check(const struct programmer_t * const pgm, const struct pin_checklist_t * const checklist, const int size, bool output) { int pins_check(const struct programmer_t *const pgm, const struct pin_checklist_t *const checklist, const int size, const bool output) {
static const struct pindef_t no_valid_pins = {{0}, {0}}; // default value if check list does not contain anything else static const struct pindef_t no_valid_pins = {{0}, {0}}; // default value if check list does not contain anything else
int rv = 0; // return value int rv = 0; // return value
int pinname; // loop counter through pinnames int pinname; // loop counter through pinnames

View File

@ -292,7 +292,7 @@ static int ser_open(char * port, union pinfo pinfo, union filedescriptor *fdp)
if (hComPort == INVALID_HANDLE_VALUE) { if (hComPort == INVALID_HANDLE_VALUE) {
const char *error = last_error_string(0); const char *error = last_error_string(0);
avrdude_message(MSG_INFO, "%s: ser_open(): can't open device \"%s\": %s\n", progname, port, error); avrdude_message(MSG_INFO, "%s: ser_open(): can't open device \"%s\": %s\n", progname, port, error);
free(error); free((char *)error);
return -1; return -1;
} }
@ -460,10 +460,10 @@ static int ser_send(union filedescriptor *fd, const unsigned char * buf, size_t
serial_w32SetTimeOut(hComPort,500); serial_w32SetTimeOut(hComPort,500);
if (!WriteFile(hComPort, buf, buflen, &written, NULL)) { if (!WriteFile(hComPort, buf, (DWORD)buflen, &written, NULL)) {
const char *error = last_error_string(0); const char *error = last_error_string(0);
avrdude_message(MSG_INFO, "%s: ser_send(): write error: %s\n", progname, error); avrdude_message(MSG_INFO, "%s: ser_send(): write error: %s\n", progname, error);
free(error); free((char *)error);
return -1; return -1;
} }
@ -576,10 +576,10 @@ static int ser_recv(union filedescriptor *fd, unsigned char * buf, size_t buflen
serial_w32SetTimeOut(hComPort, serial_recv_timeout); serial_w32SetTimeOut(hComPort, serial_recv_timeout);
if (!ReadFile(hComPort, buf, buflen, &read, NULL)) { if (!ReadFile(hComPort, buf, (DWORD)buflen, &read, NULL)) {
const char *error = last_error_string(0); const char *error = last_error_string(0);
avrdude_message(MSG_INFO, "%s: ser_recv(): read error: %s\n", progname, error); avrdude_message(MSG_INFO, "%s: ser_recv(): read error: %s\n", progname, error);
free(error); free((char *)error);
return -1; return -1;
} }
@ -642,7 +642,7 @@ static int ser_drain(union filedescriptor *fd, int display)
if (!readres) { if (!readres) {
const char *error = last_error_string(0); const char *error = last_error_string(0);
avrdude_message(MSG_INFO, "%s: ser_drain(): read error: %s\n", progname, error); avrdude_message(MSG_INFO, "%s: ser_drain(): read error: %s\n", progname, error);
free(error); free((char *)error);
return -1; return -1;
} }

View File

@ -308,8 +308,8 @@ static int serbb_open(PROGRAMMER *pgm, char *port)
progname, port); progname, port);
return -1; return -1;
} }
avrdude_message(MSG_DEBUG, "%s: ser_open(): opened comm port \"%s\", handle 0x%x\n", avrdude_message(MSG_DEBUG, "%s: ser_open(): opened comm port \"%s\", handle %p\n",
progname, port, (int)hComPort); progname, port, (void *)hComPort);
pgm->fd.pfd = (void *)hComPort; pgm->fd.pfd = (void *)hComPort;
@ -326,8 +326,8 @@ static void serbb_close(PROGRAMMER *pgm)
pgm->setpin(pgm, PIN_AVR_RESET, 1); pgm->setpin(pgm, PIN_AVR_RESET, 1);
CloseHandle (hComPort); CloseHandle (hComPort);
} }
avrdude_message(MSG_DEBUG, "%s: ser_close(): closed comm port handle 0x%x\n", avrdude_message(MSG_DEBUG, "%s: ser_close(): closed comm port handle %p\n",
progname, (int)hComPort); progname, (void *)hComPort);
hComPort = INVALID_HANDLE_VALUE; hComPort = INVALID_HANDLE_VALUE;
} }

View File

@ -504,7 +504,7 @@ static int stk500_initialize(PROGRAMMER * pgm, AVRPART * p)
} }
else { else {
buf[9] = 0xff; buf[9] = 0xff;
buf[10] = 0xff; buf[10] = 0xff;
buf[13] = 0; buf[13] = 0;
buf[14] = 0; buf[14] = 0;
buf[17] = 0; buf[17] = 0;
@ -821,7 +821,7 @@ static int stk500_paged_write(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m,
break; break;
} }
for (prusa3d_semicolon_workaround_round = 0; prusa3d_semicolon_workaround_round < (has_semicolon ? 2 : 1); ++ prusa3d_semicolon_workaround_round) { for (prusa3d_semicolon_workaround_round = 0; prusa3d_semicolon_workaround_round < (has_semicolon ? 2u : 1u); prusa3d_semicolon_workaround_round++) {
/* build command block and avoid multiple send commands as it leads to a crash /* build command block and avoid multiple send commands as it leads to a crash
of the silabs usb serial driver on mac os x */ of the silabs usb serial driver on mac os x */
i = 0; i = 0;
@ -834,7 +834,7 @@ static int stk500_paged_write(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m,
buf[i++] = block_size & 0x0f; buf[i++] = block_size & 0x0f;
buf[i++] = memtype; buf[i++] = memtype;
if (has_semicolon) { if (has_semicolon) {
for (j = 0; j < block_size; ++i, ++ j) { for (j = 0; j < (unsigned)block_size; ++i, ++ j) {
buf[i] = m->buf[addr + j]; buf[i] = m->buf[addr + j];
if (buf[i] == ';') if (buf[i] == ';')
buf[i] |= (prusa3d_semicolon_workaround_round ? 0xf0 : 0x0f); buf[i] |= (prusa3d_semicolon_workaround_round ? 0xf0 : 0x0f);
@ -1088,7 +1088,7 @@ static int stk500_set_sck_period(PROGRAMMER * pgm, double v)
min = 8.0 / STK500_XTAL; min = 8.0 / STK500_XTAL;
max = 255 * min; max = 255 * min;
dur = v / min + 0.5; dur = (int)(v / min + 0.5);
if (v < min) { if (v < min) {
dur = 1; dur = 1;

View File

@ -130,58 +130,58 @@ struct jtagispentry
#define SZ_SPI_MULTI (USHRT_MAX - 1) #define SZ_SPI_MULTI (USHRT_MAX - 1)
}; };
static const struct jtagispentry jtagispcmds[] = { // static const struct jtagispentry jtagispcmds[] = {
/* generic */ // /* generic */
{ CMD_SET_PARAMETER, 2 }, // { CMD_SET_PARAMETER, 2 },
{ CMD_GET_PARAMETER, 3 }, // { CMD_GET_PARAMETER, 3 },
{ CMD_OSCCAL, 2 }, // { CMD_OSCCAL, 2 },
{ CMD_LOAD_ADDRESS, 2 }, // { CMD_LOAD_ADDRESS, 2 },
/* ISP mode */ // /* ISP mode */
{ CMD_ENTER_PROGMODE_ISP, 2 }, // { CMD_ENTER_PROGMODE_ISP, 2 },
{ CMD_LEAVE_PROGMODE_ISP, 2 }, // { CMD_LEAVE_PROGMODE_ISP, 2 },
{ CMD_CHIP_ERASE_ISP, 2 }, // { CMD_CHIP_ERASE_ISP, 2 },
{ CMD_PROGRAM_FLASH_ISP, 2 }, // { CMD_PROGRAM_FLASH_ISP, 2 },
{ CMD_READ_FLASH_ISP, SZ_READ_FLASH_EE }, // { CMD_READ_FLASH_ISP, SZ_READ_FLASH_EE },
{ CMD_PROGRAM_EEPROM_ISP, 2 }, // { CMD_PROGRAM_EEPROM_ISP, 2 },
{ CMD_READ_EEPROM_ISP, SZ_READ_FLASH_EE }, // { CMD_READ_EEPROM_ISP, SZ_READ_FLASH_EE },
{ CMD_PROGRAM_FUSE_ISP, 3 }, // { CMD_PROGRAM_FUSE_ISP, 3 },
{ CMD_READ_FUSE_ISP, 4 }, // { CMD_READ_FUSE_ISP, 4 },
{ CMD_PROGRAM_LOCK_ISP, 3 }, // { CMD_PROGRAM_LOCK_ISP, 3 },
{ CMD_READ_LOCK_ISP, 4 }, // { CMD_READ_LOCK_ISP, 4 },
{ CMD_READ_SIGNATURE_ISP, 4 }, // { CMD_READ_SIGNATURE_ISP, 4 },
{ CMD_READ_OSCCAL_ISP, 4 }, // { CMD_READ_OSCCAL_ISP, 4 },
{ CMD_SPI_MULTI, SZ_SPI_MULTI }, // { CMD_SPI_MULTI, SZ_SPI_MULTI },
/* all HV modes */ // /* all HV modes */
{ CMD_SET_CONTROL_STACK, 2 }, // { CMD_SET_CONTROL_STACK, 2 },
/* HVSP mode */ // /* HVSP mode */
{ CMD_ENTER_PROGMODE_HVSP, 2 }, // { CMD_ENTER_PROGMODE_HVSP, 2 },
{ CMD_LEAVE_PROGMODE_HVSP, 2 }, // { CMD_LEAVE_PROGMODE_HVSP, 2 },
{ CMD_CHIP_ERASE_HVSP, 2 }, // { CMD_CHIP_ERASE_HVSP, 2 },
{ CMD_PROGRAM_FLASH_HVSP, 2 }, // { CMD_PROGRAM_FLASH_HVSP, 2 },
{ CMD_READ_FLASH_HVSP, SZ_READ_FLASH_EE }, // { CMD_READ_FLASH_HVSP, SZ_READ_FLASH_EE },
{ CMD_PROGRAM_EEPROM_HVSP, 2 }, // { CMD_PROGRAM_EEPROM_HVSP, 2 },
{ CMD_READ_EEPROM_HVSP, SZ_READ_FLASH_EE }, // { CMD_READ_EEPROM_HVSP, SZ_READ_FLASH_EE },
{ CMD_PROGRAM_FUSE_HVSP, 2 }, // { CMD_PROGRAM_FUSE_HVSP, 2 },
{ CMD_READ_FUSE_HVSP, 3 }, // { CMD_READ_FUSE_HVSP, 3 },
{ CMD_PROGRAM_LOCK_HVSP, 2 }, // { CMD_PROGRAM_LOCK_HVSP, 2 },
{ CMD_READ_LOCK_HVSP, 3 }, // { CMD_READ_LOCK_HVSP, 3 },
{ CMD_READ_SIGNATURE_HVSP, 3 }, // { CMD_READ_SIGNATURE_HVSP, 3 },
{ CMD_READ_OSCCAL_HVSP, 3 }, // { CMD_READ_OSCCAL_HVSP, 3 },
/* PP mode */ // /* PP mode */
{ CMD_ENTER_PROGMODE_PP, 2 }, // { CMD_ENTER_PROGMODE_PP, 2 },
{ CMD_LEAVE_PROGMODE_PP, 2 }, // { CMD_LEAVE_PROGMODE_PP, 2 },
{ CMD_CHIP_ERASE_PP, 2 }, // { CMD_CHIP_ERASE_PP, 2 },
{ CMD_PROGRAM_FLASH_PP, 2 }, // { CMD_PROGRAM_FLASH_PP, 2 },
{ CMD_READ_FLASH_PP, SZ_READ_FLASH_EE }, // { CMD_READ_FLASH_PP, SZ_READ_FLASH_EE },
{ CMD_PROGRAM_EEPROM_PP, 2 }, // { CMD_PROGRAM_EEPROM_PP, 2 },
{ CMD_READ_EEPROM_PP, SZ_READ_FLASH_EE }, // { CMD_READ_EEPROM_PP, SZ_READ_FLASH_EE },
{ CMD_PROGRAM_FUSE_PP, 2 }, // { CMD_PROGRAM_FUSE_PP, 2 },
{ CMD_READ_FUSE_PP, 3 }, // { CMD_READ_FUSE_PP, 3 },
{ CMD_PROGRAM_LOCK_PP, 2 }, // { CMD_PROGRAM_LOCK_PP, 2 },
{ CMD_READ_LOCK_PP, 3 }, // { CMD_READ_LOCK_PP, 3 },
{ CMD_READ_SIGNATURE_PP, 3 }, // { CMD_READ_SIGNATURE_PP, 3 },
{ CMD_READ_OSCCAL_PP, 3 }, // { CMD_READ_OSCCAL_PP, 3 },
}; // };
/* /*
* From XML file: * From XML file:
@ -379,15 +379,15 @@ static void stk500v2_jtag3_teardown(PROGRAMMER * pgm)
} }
static unsigned short // static unsigned short
b2_to_u16(unsigned char *b) // b2_to_u16(unsigned char *b)
{ // {
unsigned short l; // unsigned short l;
l = b[0]; // l = b[0];
l += (unsigned)b[1] << 8; // l += (unsigned)b[1] << 8;
return l; // return l;
} // }
static int stk500v2_send_mk2(PROGRAMMER * pgm, unsigned char * data, size_t len) static int stk500v2_send_mk2(PROGRAMMER * pgm, unsigned char * data, size_t len)
{ {
@ -399,16 +399,16 @@ static int stk500v2_send_mk2(PROGRAMMER * pgm, unsigned char * data, size_t len)
return 0; return 0;
} }
static unsigned short get_jtagisp_return_size(unsigned char cmd) // static unsigned short get_jtagisp_return_size(unsigned char cmd)
{ // {
int i; // int i;
for (i = 0; i < sizeof jtagispcmds / sizeof jtagispcmds[0]; i++) // for (i = 0; i < sizeof jtagispcmds / sizeof jtagispcmds[0]; i++)
if (jtagispcmds[i].cmd == cmd) // if (jtagispcmds[i].cmd == cmd)
return jtagispcmds[i].size; // return jtagispcmds[i].size;
return 0; // return 0;
} // }
/* /*
* Send the data as a JTAG ICE mkII encapsulated ISP packet. * Send the data as a JTAG ICE mkII encapsulated ISP packet.
@ -504,7 +504,7 @@ static int stk500v2_send(PROGRAMMER * pgm, unsigned char * data, size_t len)
buf[0] = MESSAGE_START; buf[0] = MESSAGE_START;
buf[1] = PDATA(pgm)->command_sequence; buf[1] = PDATA(pgm)->command_sequence;
buf[2] = len / 256; buf[2] = (char)(len / 256);
buf[3] = len % 256; buf[3] = len % 256;
buf[4] = TOKEN; buf[4] = TOKEN;
memcpy(buf+5, data, len); memcpy(buf+5, data, len);
@ -1128,7 +1128,8 @@ static int stk500v2_program_enable(PROGRAMMER * pgm, AVRPART * p)
{ {
unsigned char buf[16]; unsigned char buf[16];
char msg[100]; /* see remarks above about size needed */ char msg[100]; /* see remarks above about size needed */
int rv, tries; int rv;
// int tries;
PDATA(pgm)->lastpart = p; PDATA(pgm)->lastpart = p;
@ -1143,7 +1144,7 @@ static int stk500v2_program_enable(PROGRAMMER * pgm, AVRPART * p)
/* Activate AVR-style (low active) RESET */ /* Activate AVR-style (low active) RESET */
stk500v2_setparm_real(pgm, PARAM_RESET_POLARITY, 0x01); stk500v2_setparm_real(pgm, PARAM_RESET_POLARITY, 0x01);
tries = 0; // tries = 0;
// retry: // retry:
buf[0] = CMD_ENTER_PROGMODE_ISP; buf[0] = CMD_ENTER_PROGMODE_ISP;
buf[1] = p->timeout; buf[1] = p->timeout;
@ -1882,7 +1883,7 @@ static int stk500hv_read_byte(PROGRAMMER * pgm, AVRPART * p, AVRMEM * mem,
if (stk500v2_loadaddr(pgm, use_ext_addr | (paddr >> addrshift)) < 0) if (stk500v2_loadaddr(pgm, use_ext_addr | (paddr >> addrshift)) < 0)
return -1; return -1;
} else { } else {
buf[1] = addr; buf[1] = (char)addr;
} }
avrdude_message(MSG_NOTICE2, "%s: stk500hv_read_byte(): Sending read memory command: ", avrdude_message(MSG_NOTICE2, "%s: stk500hv_read_byte(): Sending read memory command: ",
@ -2137,7 +2138,7 @@ static int stk500hv_write_byte(PROGRAMMER * pgm, AVRPART * p, AVRMEM * mem,
if (stk500v2_loadaddr(pgm, use_ext_addr | (paddr >> addrshift)) < 0) if (stk500v2_loadaddr(pgm, use_ext_addr | (paddr >> addrshift)) < 0)
return -1; return -1;
} else { } else {
buf[1] = addr; buf[1] = (char)addr;
buf[2] = data; buf[2] = data;
if (mode == PPMODE) { if (mode == PPMODE) {
buf[3] = pulsewidth; buf[3] = pulsewidth;
@ -2298,7 +2299,7 @@ static int stk500v2_paged_write(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m,
unsigned int page_size, unsigned int page_size,
unsigned int addr, unsigned int n_bytes) unsigned int addr, unsigned int n_bytes)
{ {
static int page = 0; // static int page = 0;
unsigned int block_size, last_addr, addrshift, use_ext_addr; unsigned int block_size, last_addr, addrshift, use_ext_addr;
unsigned int maxaddr = addr + n_bytes; unsigned int maxaddr = addr + n_bytes;
unsigned char commandbuf[10]; unsigned char commandbuf[10];
@ -2833,10 +2834,10 @@ static int stk500v2_set_fosc(PROGRAMMER * pgm, double v)
progname, v, unit, STK500V2_XTAL / 2e6); progname, v, unit, STK500V2_XTAL / 2e6);
fosc = STK500V2_XTAL / 2; fosc = STK500V2_XTAL / 2;
} else } else
fosc = (unsigned)v; fosc = (int)v;
for (idx = 0; idx < sizeof(ps) / sizeof(ps[0]); idx++) { for (idx = 0; idx < sizeof(ps) / sizeof(ps[0]); idx++) {
if (fosc >= STK500V2_XTAL / (256 * ps[idx] * 2)) { if (fosc >= (int)(STK500V2_XTAL / (256 * ps[idx] * 2))) {
/* this prescaler value can handle our frequency */ /* this prescaler value can handle our frequency */
prescale = idx + 1; prescale = idx + 1;
cmatch = (unsigned)(STK500V2_XTAL / (2 * fosc * ps[idx])) - 1; cmatch = (unsigned)(STK500V2_XTAL / (2 * fosc * ps[idx])) - 1;
@ -3065,8 +3066,8 @@ static int stk600_set_fosc(PROGRAMMER * pgm, double v)
{ {
unsigned int oct, dac; unsigned int oct, dac;
oct = 1.443 * log(v / 1039.0); oct = (unsigned)(1.443 * log(v / 1039.0));
dac = 2048 - (2078.0 * pow(2, (double)(10 + oct))) / v; dac = (unsigned)(2048.0 - (2078.0 * pow(2, (double)(10 + oct))) / v);
return stk500v2_setparm2(pgm, PARAM2_CLOCK_CONF, (oct << 12) | (dac << 2)); return stk500v2_setparm2(pgm, PARAM2_CLOCK_CONF, (oct << 12) | (dac << 2));
} }
@ -3075,7 +3076,7 @@ static int stk600_set_sck_period(PROGRAMMER * pgm, double v)
{ {
unsigned int sck; unsigned int sck;
sck = ceil((16e6 / (2 * 1.0 / v)) - 1); sck = (unsigned)ceil((16e6 / (2 * 1.0 / v)) - 1);
if (sck >= 4096) if (sck >= 4096)
sck = 4095; sck = 4095;
@ -3093,7 +3094,7 @@ static int stk500v2_jtag3_set_sck_period(PROGRAMMER * pgm, double v)
else if (v > 1E-3) else if (v > 1E-3)
sck = 1; sck = 1;
else else
sck = 1.0 / (1000.0 * v); sck = (unsigned)(1.0 / (1000.0 * v));
value[0] = CMD_SET_SCK; value[0] = CMD_SET_SCK;
value[1] = sck & 0xff; value[1] = sck & 0xff;
@ -3143,7 +3144,7 @@ static int stk500v2_setparm_real(PROGRAMMER * pgm, unsigned char parm, unsigned
static int stk500v2_setparm(PROGRAMMER * pgm, unsigned char parm, unsigned char value) static int stk500v2_setparm(PROGRAMMER * pgm, unsigned char parm, unsigned char value)
{ {
unsigned char current_value; unsigned char current_value = 0;
int res; int res;
res = stk500v2_getparm(pgm, parm, &current_value); res = stk500v2_getparm(pgm, parm, &current_value);
@ -3214,8 +3215,15 @@ static const char *stk600_get_cardname(const struct carddata *table,
static void stk500v2_display(PROGRAMMER * pgm, const char * p) static void stk500v2_display(PROGRAMMER * pgm, const char * p)
{ {
unsigned char maj, min, hdw, topcard, maj_s1, min_s1, maj_s2, min_s2; unsigned char maj = 0;
unsigned int rev; unsigned char min = 0;
unsigned char hdw = 0;
unsigned char topcard = 0;
unsigned char maj_s1 = 0;
unsigned char min_s1 = 0;
unsigned char maj_s2 = 0;
unsigned char min_s2 = 0;
unsigned int rev = 0;
const char *topcard_name, *pgmname; const char *topcard_name, *pgmname;
switch (PDATA(pgm)->pgmtype) { switch (PDATA(pgm)->pgmtype) {
@ -3294,13 +3302,20 @@ f_to_kHz_MHz(double f, const char **unit)
static void stk500v2_print_parms1(PROGRAMMER * pgm, const char * p) static void stk500v2_print_parms1(PROGRAMMER * pgm, const char * p)
{ {
unsigned char vtarget, vadjust, osc_pscale, osc_cmatch, sck_duration =0; //XXX 0 is not correct, check caller unsigned char vtarget = 0;
unsigned int sck_stk600, clock_conf, dac, oct, varef; unsigned char vadjust = 0;
unsigned char vtarget_jtag[4]; unsigned char sck_duration = 0;
unsigned char osc_pscale = 0;
unsigned char osc_cmatch = 0;
unsigned varef = 0;
unsigned sck_stk600 = 0;
unsigned clock_conf = 0;
unsigned dac, oct;
// unsigned char vtarget_jtag[4];
int prescale; int prescale;
double f; double f;
const char *unit; const char *unit;
void *mycookie; // void *mycookie;
if (PDATA(pgm)->pgmtype == PGMTYPE_JTAGICE_MKII) { if (PDATA(pgm)->pgmtype == PGMTYPE_JTAGICE_MKII) {
return; return;
@ -3963,10 +3978,10 @@ static int stk600_xprog_write_byte(PROGRAMMER * pgm, AVRPART * p, AVRMEM * mem,
b[0] = XPRG_CMD_WRITE_MEM; b[0] = XPRG_CMD_WRITE_MEM;
b[1] = memcode; b[1] = memcode;
b[2] = 0; /* pagemode: non-paged write */ b[2] = 0; /* pagemode: non-paged write */
b[3] = addr >> 24; b[3] = (char)(addr >> 24);
b[4] = addr >> 16; b[4] = (char)(addr >> 16);
b[5] = addr >> 8; b[5] = (char)(addr >> 8);
b[6] = addr; b[6] = (char)addr;
b[7] = 0; b[7] = 0;
b[8] = write_size; b[8] = write_size;
b[9] = data; b[9] = data;
@ -4011,10 +4026,10 @@ static int stk600_xprog_read_byte(PROGRAMMER * pgm, AVRPART * p, AVRMEM * mem,
addr += mem->offset; addr += mem->offset;
b[0] = XPRG_CMD_READ_MEM; b[0] = XPRG_CMD_READ_MEM;
b[2] = addr >> 24; b[2] = (char)(addr >> 24);
b[3] = addr >> 16; b[3] = (char)(addr >> 16);
b[4] = addr >> 8; b[4] = (char)(addr >> 8);
b[5] = addr; b[5] = (char)addr;
b[6] = 0; b[6] = 0;
b[7] = 1; b[7] = 1;
if (stk600_xprog_command(pgm, b, 8, 3) < 0) { if (stk600_xprog_command(pgm, b, 8, 3) < 0) {

View File

@ -281,7 +281,7 @@ static int cmd_dump(PROGRAMMER * pgm, struct avrpart * p,
maxsize = mem->size; maxsize = mem->size;
if (addr >= maxsize) { if (addr >= (unsigned long)maxsize) {
if (argc == 2) { if (argc == 2) {
/* wrap around */ /* wrap around */
addr = 0; addr = 0;
@ -294,7 +294,7 @@ static int cmd_dump(PROGRAMMER * pgm, struct avrpart * p,
} }
/* trim len if nessary to not read past the end of memory */ /* trim len if nessary to not read past the end of memory */
if ((addr + len) > maxsize) if ((addr + len) > (unsigned long)maxsize)
len = maxsize - addr; len = maxsize - addr;
buf = malloc(len); buf = malloc(len);
@ -303,7 +303,7 @@ static int cmd_dump(PROGRAMMER * pgm, struct avrpart * p,
return -1; return -1;
} }
for (i=0; i<len; i++) { for (i = 0; i < (unsigned long)len; i++) {
rc = pgm->read_byte(pgm, p, mem, addr+i, &buf[i]); rc = pgm->read_byte(pgm, p, mem, addr+i, &buf[i]);
if (rc != 0) { if (rc != 0) {
avrdude_message(MSG_INFO, "error reading %s address 0x%05lx of part %s\n", avrdude_message(MSG_INFO, "error reading %s address 0x%05lx of part %s\n",
@ -364,7 +364,7 @@ static int cmd_write(PROGRAMMER * pgm, struct avrpart * p,
return -1; return -1;
} }
if (addr > maxsize) { if (addr > (unsigned long)maxsize) {
avrdude_message(MSG_INFO, "%s (write): address 0x%05lx is out of range for %s memory\n", avrdude_message(MSG_INFO, "%s (write): address 0x%05lx is out of range for %s memory\n",
progname, addr, memtype); progname, addr, memtype);
return -1; return -1;
@ -373,7 +373,7 @@ static int cmd_write(PROGRAMMER * pgm, struct avrpart * p,
/* number of bytes to write at the specified address */ /* number of bytes to write at the specified address */
len = argc - 3; len = argc - 3;
if ((addr + len) > maxsize) { if ((addr + len) > (unsigned long)maxsize) {
avrdude_message(MSG_INFO, "%s (write): selected address and # bytes exceed " avrdude_message(MSG_INFO, "%s (write): selected address and # bytes exceed "
"range for %s memory\n", "range for %s memory\n",
progname, memtype); progname, memtype);
@ -386,8 +386,8 @@ static int cmd_write(PROGRAMMER * pgm, struct avrpart * p,
return -1; return -1;
} }
for (i=3; i<argc; i++) { for (i = 3; i < (unsigned long)argc; i++) {
buf[i-3] = strtoul(argv[i], &e, 0); buf[i-3] = (char)strtoul(argv[i], &e, 0);
if (*e || (e == argv[i])) { if (*e || (e == argv[i])) {
avrdude_message(MSG_INFO, "%s (write): can't parse byte \"%s\"\n", avrdude_message(MSG_INFO, "%s (write): can't parse byte \"%s\"\n",
progname, argv[i]); progname, argv[i]);
@ -397,7 +397,7 @@ static int cmd_write(PROGRAMMER * pgm, struct avrpart * p,
} }
pgm->err_led(pgm, OFF); pgm->err_led(pgm, OFF);
for (werror=0, i=0; i<len; i++) { for (werror = 0, i = 0; i < (unsigned long)len; i++) {
rc = avr_write_byte(pgm, p, mem, addr+i, buf[i]); rc = avr_write_byte(pgm, p, mem, addr+i, buf[i]);
if (rc) { if (rc) {
@ -462,7 +462,7 @@ static int cmd_send(PROGRAMMER * pgm, struct avrpart * p,
/* load command bytes */ /* load command bytes */
for (i=1; i<argc; i++) { for (i=1; i<argc; i++) {
cmd[i-1] = strtoul(argv[i], &e, 0); cmd[i-1] = (char)strtoul(argv[i], &e, 0);
if (*e || (e == argv[i])) { if (*e || (e == argv[i])) {
avrdude_message(MSG_INFO, "%s (send): can't parse byte \"%s\"\n", avrdude_message(MSG_INFO, "%s (send): can't parse byte \"%s\"\n",
progname, argv[i]); progname, argv[i]);
@ -789,7 +789,7 @@ static int tokenize(char * s, char *** argv)
char * nbuf; char * nbuf;
char ** av; char ** av;
slen = strlen(s); slen = (int)strlen(s);
/* /*
* initialize allow for 20 arguments, use realloc to grow this if * initialize allow for 20 arguments, use realloc to grow this if
@ -812,7 +812,7 @@ static int tokenize(char * s, char *** argv)
nexttok(r, &q, &r); nexttok(r, &q, &r);
strcpy(nbuf, q); strcpy(nbuf, q);
bufv[n] = nbuf; bufv[n] = nbuf;
len = strlen(q); len = (int)strlen(q);
l += len + 1; l += len + 1;
nbuf += len + 1; nbuf += len + 1;
nbuf[0] = 0; nbuf[0] = 0;
@ -841,7 +841,7 @@ static int tokenize(char * s, char *** argv)
q = (char *)&av[n+1]; q = (char *)&av[n+1];
memcpy(q, buf, l); memcpy(q, buf, l);
for (i=0; i<n; i++) { for (i=0; i<n; i++) {
offset = bufv[i] - buf; offset = (int)(bufv[i] - buf);
av[i] = q + offset; av[i] = q + offset;
} }
av[i] = NULL; av[i] = NULL;
@ -862,7 +862,7 @@ static int do_cmd(PROGRAMMER * pgm, struct avrpart * p,
int hold; int hold;
int len; int len;
len = strlen(argv[0]); len = (int)strlen(argv[0]);
hold = -1; hold = -1;
for (i=0; i<NCMDS; i++) { for (i=0; i<NCMDS; i++) {
if (strcasecmp(argv[0], cmd[i].name) == 0) { if (strcasecmp(argv[0], cmd[i].name) == 0) {

View File

@ -10,5 +10,5 @@ if(libigl_FOUND)
target_link_libraries(libigl INTERFACE igl::core) target_link_libraries(libigl INTERFACE igl::core)
else() else()
message(STATUS "IGL NOT found, using bundled version...") message(STATUS "IGL NOT found, using bundled version...")
target_include_directories(libigl INTERFACE SYSTEM ${LIBDIR}/libigl) target_include_directories(libigl SYSTEM BEFORE INTERFACE ${LIBDIR}/libigl)
endif() endif()

View File

@ -10,10 +10,6 @@
#include "boost/multiprecision/integer.hpp" #include "boost/multiprecision/integer.hpp"
#include "boost/rational.hpp" #include "boost/rational.hpp"
//#include "../tools/Int128.hpp"
//#include "gte/Mathematics/GteMinimumAreaBox2.h"
//#include "../tools/libnfpglue.hpp" //#include "../tools/libnfpglue.hpp"
//#include "../tools/nfp_svgnest_glue.hpp" //#include "../tools/nfp_svgnest_glue.hpp"
@ -159,12 +155,12 @@ TEST(GeometryAlgorithms, boundingCircle) {
if(std::isnan(c.radius())) std::cout << "fail: radius is nan" << std::endl; if(std::isnan(c.radius())) std::cout << "fail: radius is nan" << std::endl;
else for(auto v : shapelike::contour(part.transformedShape()) ) { else for(auto v : shapelike::contour(part.transformedShape()) ) {
auto d = pointlike::distance(v, c.center()); auto d = pointlike::distance(v, c.center());
if(d > c.radius() ) { if(d > c.radius() ) {
auto e = std::abs( 1.0 - d/c.radius()); auto e = std::abs( 1.0 - d/c.radius());
ASSERT_LE(e, 1e-3); ASSERT_LE(e, 1e-3);
}
} }
}
i++; i++;
} }
@ -183,7 +179,7 @@ TEST(GeometryAlgorithms, Distance) {
Segment seg(p1, p3); Segment seg(p1, p3);
// ASSERT_DOUBLE_EQ(pointlike::distance(p2, seg), 7.0710678118654755); // ASSERT_DOUBLE_EQ(pointlike::distance(p2, seg), 7.0710678118654755);
auto result = pointlike::horizontalDistance(p2, seg); auto result = pointlike::horizontalDistance(p2, seg);
@ -302,12 +298,12 @@ TEST(GeometryAlgorithms, LeftAndDownPolygon)
{35, 35}, {35, 55}, {40, 75}, {70, 75}}; {35, 35}, {35, 55}, {40, 75}, {70, 75}};
Item leftControl = { {40, 75}, Item leftControl = { {40, 75},
{35, 55}, {35, 55},
{35, 35}, {35, 35},
{42, 20}, {42, 20},
{0, 20}, {0, 20},
{0, 75}, {0, 75},
{40, 75}}; {40, 75}};
Item downControl = {{88, 60}, Item downControl = {{88, 60},
{88, 0}, {88, 0},
@ -396,7 +392,7 @@ TEST(GeometryAlgorithms, ArrangeRectanglesLoose)
{ {
using namespace libnest2d; using namespace libnest2d;
// std::vector<Rectangle> rects = { {40, 40}, {10, 10}, {20, 20} }; // std::vector<Rectangle> rects = { {40, 40}, {10, 10}, {20, 20} };
std::vector<Rectangle> rects = { std::vector<Rectangle> rects = {
{80, 80}, {80, 80},
{60, 90}, {60, 90},
@ -422,7 +418,7 @@ TEST(GeometryAlgorithms, ArrangeRectanglesLoose)
Coord min_obj_distance = 5; Coord min_obj_distance = 5;
Nester<BottomLeftPlacer, DJDHeuristic> arrange(Box(210, 250), Nester<BottomLeftPlacer, DJDHeuristic> arrange(Box(210, 250),
min_obj_distance); min_obj_distance);
auto groups = arrange(rects.begin(), rects.end()); auto groups = arrange(rects.begin(), rects.end());
@ -454,41 +450,41 @@ void exportSVG(std::vector<std::reference_wrapper<Item>>& result, const Bin& bin
std::string loc = "out"; std::string loc = "out";
static std::string svg_header = static std::string svg_header =
R"raw(<?xml version="1.0" encoding="UTF-8" standalone="yes"?> R"raw(<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.0//EN" "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd"> <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.0//EN" "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd">
<svg height="500" width="500" xmlns="http://www.w3.org/2000/svg" xmlns:svg="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"> <svg height="500" width="500" xmlns="http://www.w3.org/2000/svg" xmlns:svg="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
)raw"; )raw";
int i = idx; int i = idx;
auto r = result; auto r = result;
// for(auto r : result) { // for(auto r : result) {
std::fstream out(loc + std::to_string(i) + ".svg", std::fstream::out); std::fstream out(loc + std::to_string(i) + ".svg", std::fstream::out);
if(out.is_open()) { if(out.is_open()) {
out << svg_header; out << svg_header;
Item rbin( Rectangle(bin.width(), bin.height()) ); Item rbin( Rectangle(bin.width(), bin.height()) );
for(unsigned i = 0; i < rbin.vertexCount(); i++) { for(unsigned i = 0; i < rbin.vertexCount(); i++) {
auto v = rbin.vertex(i); auto v = rbin.vertex(i);
setY(v, -getY(v)/SCALE + 500 ); setY(v, -getY(v)/SCALE + 500 );
setX(v, getX(v)/SCALE); setX(v, getX(v)/SCALE);
rbin.setVertex(i, v); rbin.setVertex(i, v);
}
out << shapelike::serialize<Formats::SVG>(rbin.rawShape()) << std::endl;
for(Item& sh : r) {
Item tsh(sh.transformedShape());
for(unsigned i = 0; i < tsh.vertexCount(); i++) {
auto v = tsh.vertex(i);
setY(v, -getY(v)/SCALE + 500);
setX(v, getX(v)/SCALE);
tsh.setVertex(i, v);
}
out << shapelike::serialize<Formats::SVG>(tsh.rawShape()) << std::endl;
}
out << "\n</svg>" << std::endl;
} }
out.close(); out << shapelike::serialize<Formats::SVG>(rbin.rawShape()) << std::endl;
for(Item& sh : r) {
Item tsh(sh.transformedShape());
for(unsigned i = 0; i < tsh.vertexCount(); i++) {
auto v = tsh.vertex(i);
setY(v, -getY(v)/SCALE + 500);
setX(v, getX(v)/SCALE);
tsh.setVertex(i, v);
}
out << shapelike::serialize<Formats::SVG>(tsh.rawShape()) << std::endl;
}
out << "\n</svg>" << std::endl;
}
out.close();
// i++; // i++;
// } // }
} }
} }
@ -556,13 +552,14 @@ TEST(GeometryAlgorithms, NestTest) {
ASSERT_LE(result.size(), 2); ASSERT_LE(result.size(), 2);
int partsum = std::accumulate(result.begin(), size_t partsum = std::accumulate(result.begin(),
result.end(), result.end(),
0, size_t(0),
[](int s, [](size_t s,
const decltype(result)::value_type &bin) { const decltype(
return s += bin.size(); result)::value_type &bin) {
}); return s += bin.size();
});
ASSERT_EQ(input.size(), partsum); ASSERT_EQ(input.size(), partsum);
} }
@ -647,7 +644,7 @@ std::vector<ItemPair> nfp_testdata = {
{118, 101}, {118, 101},
{117, 103}, {117, 103},
{117, 107} {117, 107}
}, },
{ {
{102, 116}, {102, 116},
{111, 126}, {111, 126},
@ -658,7 +655,7 @@ std::vector<ItemPair> nfp_testdata = {
{147, 84}, {147, 84},
{102, 84}, {102, 84},
{102, 116}, {102, 116},
} }
}, },
{ {
{ {
@ -674,7 +671,7 @@ std::vector<ItemPair> nfp_testdata = {
{108, 70}, {108, 70},
{99, 102}, {99, 102},
{99, 122}, {99, 122},
}, },
{ {
{107, 124}, {107, 124},
{128, 125}, {128, 125},
@ -691,7 +688,7 @@ std::vector<ItemPair> nfp_testdata = {
{108, 85}, {108, 85},
{107, 86}, {107, 86},
{107, 124}, {107, 124},
} }
}, },
{ {
{ {
@ -706,7 +703,7 @@ std::vector<ItemPair> nfp_testdata = {
{132, 57}, {132, 57},
{91, 98}, {91, 98},
{91, 100}, {91, 100},
}, },
{ {
{101, 90}, {101, 90},
{103, 98}, {103, 98},
@ -724,50 +721,50 @@ std::vector<ItemPair> nfp_testdata = {
{102, 87}, {102, 87},
{101, 89}, {101, 89},
{101, 90}, {101, 90},
} }
} }
}; };
std::vector<ItemPair> nfp_concave_testdata = { std::vector<ItemPair> nfp_concave_testdata = {
{ // ItemPair { // ItemPair
{ {
{ {
{533726, 142141}, {533726, 142141},
{532359, 143386}, {532359, 143386},
{530141, 142155}, {530141, 142155},
{528649, 160091}, {528649, 160091},
{533659, 157607}, {533659, 157607},
{538669, 160091}, {538669, 160091},
{537178, 142155}, {537178, 142155},
{534959, 143386}, {534959, 143386},
{533726, 142141}, {533726, 142141},
} }
}, },
{ {
{ {
{118305, 11603}, {118305, 11603},
{118311, 26616}, {118311, 26616},
{113311, 26611}, {113311, 26611},
{109311, 29604}, {109311, 29604},
{109300, 44608}, {109300, 44608},
{109311, 49631}, {109311, 49631},
{113300, 52636}, {113300, 52636},
{118311, 52636}, {118311, 52636},
{118308, 103636}, {118308, 103636},
{223830, 103636}, {223830, 103636},
{236845, 90642}, {236845, 90642},
{236832, 11630}, {236832, 11630},
{232825, 11616}, {232825, 11616},
{210149, 11616}, {210149, 11616},
{211308, 13625}, {211308, 13625},
{209315, 17080}, {209315, 17080},
{205326, 17080}, {205326, 17080},
{203334, 13629}, {203334, 13629},
{204493, 11616}, {204493, 11616},
{118305, 11603}, {118305, 11603},
} }
}, },
} }
}; };
template<nfp::NfpLevel lvl, Coord SCALE> template<nfp::NfpLevel lvl, Coord SCALE>
@ -935,67 +932,39 @@ template<class T> struct BoostGCD {
}; };
using Unit = int64_t; using Unit = int64_t;
using Ratio = boost::rational<boost::multiprecision::int128_t>;// Rational<boost::multiprecision::int256_t>; using Ratio = boost::rational<boost::multiprecision::int128_t>;
//double gteMinAreaBox(const PolygonImpl& p) {
// using GteCoord = ClipperLib::cInt;
// using GtePoint = gte::Vector2<GteCoord>;
// gte::MinimumAreaBox2<GteCoord, Ratio> mb;
// std::vector<GtePoint> points;
// points.reserve(p.Contour.size());
// for(auto& pt : p.Contour) points.emplace_back(GtePoint{GteCoord(pt.X), GteCoord(pt.Y)});
// mb(int(points.size()), points.data(), 0, nullptr, true);
// auto min_area = double(mb.GetArea());
// return min_area;
//}
} }
TEST(RotatingCalipers, MinAreaBBCClk) { TEST(RotatingCalipers, MinAreaBBCClk) {
// PolygonImpl poly({{-50, 30}, {-50, -50}, {50, -50}, {50, 50}, {-40, 50}});
// PolygonImpl poly({{-50, 0}, {50, 0}, {0, 100}});
auto u = [](ClipperLib::cInt n) { return n*1000000; }; auto u = [](ClipperLib::cInt n) { return n*1000000; };
PolygonImpl poly({ {u(0), u(0)}, {u(4), u(1)}, {u(2), u(4)}}); PolygonImpl poly({ {u(0), u(0)}, {u(4), u(1)}, {u(2), u(4)}});
long double arearef = refMinAreaBox(poly); long double arearef = refMinAreaBox(poly);
long double area = minAreaBoundingBox<PolygonImpl, Unit, Ratio>(poly).area(); long double area = minAreaBoundingBox<PolygonImpl, Unit, Ratio>(poly).area();
// double gtearea = gteMinAreaBox(poly);
ASSERT_LE(std::abs(area - arearef), 500e6 ); ASSERT_LE(std::abs(area - arearef), 500e6 );
// ASSERT_LE(std::abs(gtearea - arearef), 500 );
// ASSERT_DOUBLE_EQ(gtearea, arearef);
} }
TEST(RotatingCalipers, AllPrusaMinBB) { TEST(RotatingCalipers, AllPrusaMinBB) {
size_t idx = 0; // /size_t idx = 0;
long double err_epsilon = 500e6l; long double err_epsilon = 500e6l;
for(ClipperLib::Path rinput : PRINTER_PART_POLYGONS) { for(ClipperLib::Path rinput : PRINTER_PART_POLYGONS) {
// ClipperLib::Path rinput = PRINTER_PART_POLYGONS[idx]; // ClipperLib::Path rinput = PRINTER_PART_POLYGONS[idx];
// rinput.pop_back(); // rinput.pop_back();
// std::reverse(rinput.begin(), rinput.end()); // std::reverse(rinput.begin(), rinput.end());
// PolygonImpl poly(removeCollinearPoints<PathImpl, PointImpl, Unit>(rinput, 1000000)); // PolygonImpl poly(removeCollinearPoints<PathImpl, PointImpl, Unit>(rinput, 1000000));
PolygonImpl poly(rinput); PolygonImpl poly(rinput);
long double arearef = refMinAreaBox(poly); long double arearef = refMinAreaBox(poly);
auto bb = minAreaBoundingBox<PathImpl, Unit, Ratio>(rinput); auto bb = minAreaBoundingBox<PathImpl, Unit, Ratio>(rinput);
long double area = cast<long double>(bb.area()); long double area = cast<long double>(bb.area());
// double area = gteMinAreaBox(poly);
bool succ = std::abs(arearef - area) < err_epsilon; bool succ = std::abs(arearef - area) < err_epsilon;
std::cout << idx++ << " " << (succ? "ok" : "failed") << " ref: " // std::cout << idx++ << " " << (succ? "ok" : "failed") << " ref: "
<< arearef << " actual: " << area << std::endl; // << arearef << " actual: " << area << std::endl;
ASSERT_TRUE(succ); ASSERT_TRUE(succ);
} }
@ -1006,21 +975,20 @@ TEST(RotatingCalipers, AllPrusaMinBB) {
PolygonImpl poly(removeCollinearPoints<PathImpl, PointImpl, Unit>(rinput, 1000000)); PolygonImpl poly(removeCollinearPoints<PathImpl, PointImpl, Unit>(rinput, 1000000));
long double arearef = refMinAreaBox(poly); long double arearef = refMinAreaBox(poly);
auto bb = minAreaBoundingBox<PolygonImpl, Unit, Ratio>(poly); auto bb = minAreaBoundingBox<PolygonImpl, Unit, Ratio>(poly);
long double area = cast<long double>(bb.area()); long double area = cast<long double>(bb.area());
// double area = gteMinAreaBox(poly);
bool succ = std::abs(arearef - area) < err_epsilon; bool succ = std::abs(arearef - area) < err_epsilon;
std::cout << idx++ << " " << (succ? "ok" : "failed") << " ref: " // std::cout << idx++ << " " << (succ? "ok" : "failed") << " ref: "
<< arearef << " actual: " << area << std::endl; // << arearef << " actual: " << area << std::endl;
ASSERT_TRUE(succ); ASSERT_TRUE(succ);
} }
} }
int main(int argc, char **argv) { int main(int argc, char **argv) {
::testing::InitGoogleTest(&argc, argv); ::testing::InitGoogleTest(&argc, argv);
return RUN_ALL_TESTS(); return RUN_ALL_TESTS();
} }

View File

@ -760,18 +760,18 @@ bool DynamicConfig::read_cli(int argc, char** argv, t_config_option_keys* extra,
} }
// Store the option value. // Store the option value.
const bool existing = this->has(opt_key); const bool existing = this->has(opt_key);
if (keys != nullptr && !existing) { if (keys != nullptr && ! existing) {
// Save the order of detected keys. // Save the order of detected keys.
keys->push_back(opt_key); keys->push_back(opt_key);
} }
ConfigOption *opt_base = this->option(opt_key, true); ConfigOption *opt_base = this->option(opt_key, true);
ConfigOptionVectorBase *opt_vector = opt_base->is_vector() ? static_cast<ConfigOptionVectorBase*>(opt_base) : nullptr; ConfigOptionVectorBase *opt_vector = opt_base->is_vector() ? static_cast<ConfigOptionVectorBase*>(opt_base) : nullptr;
if (opt_vector) { if (opt_vector) {
if (! existing)
// remove the default values
opt_vector->clear();
// Vector values will be chained. Repeated use of a parameter will append the parameter or parameters // Vector values will be chained. Repeated use of a parameter will append the parameter or parameters
// to the end of the value. // to the end of the value.
if (!existing)
// remove the default values
opt_vector->deserialize("", true);
if (opt_base->type() == coBools) if (opt_base->type() == coBools)
static_cast<ConfigOptionBools*>(opt_base)->values.push_back(!no); static_cast<ConfigOptionBools*>(opt_base)->values.push_back(!no);
else else

View File

@ -188,8 +188,10 @@ public:
// Set a single vector item from either a scalar option or the first value of a vector option.vector of ConfigOptions. // Set a single vector item from either a scalar option or the first value of a vector option.vector of ConfigOptions.
// This function is useful to split values from multiple extrder / filament settings into separate configurations. // This function is useful to split values from multiple extrder / filament settings into separate configurations.
virtual void set_at(const ConfigOption *rhs, size_t i, size_t j) = 0; virtual void set_at(const ConfigOption *rhs, size_t i, size_t j) = 0;
// Resize the vector of values, copy the newly added values from opt_default if provided.
virtual void resize(size_t n, const ConfigOption *opt_default = nullptr) = 0; virtual void resize(size_t n, const ConfigOption *opt_default = nullptr) = 0;
// Clear the values vector.
virtual void clear() = 0;
// Get size of this vector. // Get size of this vector.
virtual size_t size() const = 0; virtual size_t size() const = 0;
@ -298,6 +300,8 @@ public:
} }
} }
// Clear the values vector.
void clear() override { this->values.clear(); }
size_t size() const override { return this->values.size(); } size_t size() const override { return this->values.size(); }
bool empty() const override { return this->values.empty(); } bool empty() const override { return this->values.empty(); }

View File

@ -721,8 +721,12 @@ void GCode::_do_export(Print &print, FILE *file)
this->m_ordered_objects.push_back(print_object); this->m_ordered_objects.push_back(print_object);
unsigned int copy_id = 0; unsigned int copy_id = 0;
for (const Point &pos : print_object->copies()) { for (const Point &pos : print_object->copies()) {
_write_format(file, "; object:{\"name\":\"%s\",\"id\":\"%s id:%d copy %d\",\"object_center\":[%f,%f,%f],\"boundingbox_center\":[%f,%f,%f],\"boundingbox_size\":[%f,%f,%f]}", std::string object_name = print_object->model_object()->name;
print_object->model_object()->name.substr(0, print_object->model_object()->name.find(".", 0)), print_object->model_object()->name, this->m_ordered_objects.size() - 1, copy_id, size_t pos_dot = object_name.find(".", 0);
if (pos_dot != std::string::npos && pos_dot > 0)
object_name = object_name.substr(0, pos_dot);
_write_format(file, "; object:{\"name\":\"%s\",\"id\":\"%s id:%d copy %d\",\"object_center\":[%f,%f,%f],\"boundingbox_center\":[%f,%f,%f],\"boundingbox_size\":[%f,%f,%f]}\n",
object_name.c_str(), print_object->model_object()->name.c_str(), this->m_ordered_objects.size() - 1, copy_id,
print_object->model_object()->bounding_box().center().x(), print_object->model_object()->bounding_box().center().y(), 0, print_object->model_object()->bounding_box().center().x(), print_object->model_object()->bounding_box().center().y(), 0,
print_object->model_object()->bounding_box().center().x(), print_object->model_object()->bounding_box().center().y(), print_object->model_object()->bounding_box().center().z(), print_object->model_object()->bounding_box().center().x(), print_object->model_object()->bounding_box().center().y(), print_object->model_object()->bounding_box().center().z(),
print_object->model_object()->bounding_box().size().x(), print_object->model_object()->bounding_box().size().y(), print_object->model_object()->bounding_box().size().z() print_object->model_object()->bounding_box().size().x(), print_object->model_object()->bounding_box().size().y(), print_object->model_object()->bounding_box().size().z()
@ -1422,7 +1426,9 @@ void GCode::process_layer(
m_colorprint_heights.erase(m_colorprint_heights.begin()); m_colorprint_heights.erase(m_colorprint_heights.begin());
colorprint_change = true; colorprint_change = true;
} }
if (colorprint_change && print.extruders().size()==1)
// we should add or not colorprint_change in respect to nozzle_diameter count instead of really used extruders count
if (colorprint_change && print./*extruders()*/config().nozzle_diameter.size()==1)
gcode += "M600\n"; gcode += "M600\n";
@ -1658,25 +1664,33 @@ void GCode::process_layer(
m_avoid_crossing_perimeters.use_external_mp = true; m_avoid_crossing_perimeters.use_external_mp = true;
for (const ExtrusionEntity *ee : print.brim().entities) for (const ExtrusionEntity *ee : print.brim().entities)
gcode += this->extrude_entity(*ee, "brim", m_config.support_material_speed.value); gcode += this->extrude_entity(*ee, "brim", m_config.support_material_speed.value);
m_brim_done = true;
m_avoid_crossing_perimeters.use_external_mp = false; m_avoid_crossing_perimeters.use_external_mp = false;
// Allow a straight travel move to the first object point. // Allow a straight travel move to the first object point.
m_avoid_crossing_perimeters.disable_once = true; m_avoid_crossing_perimeters.disable_once = true;
m_brim_done = true;
} }
//extrude object-only skirt & brim & first extruder //extrude object-only skirt
if (single_object_idx != size_t(-1) && !layers.front().object()->skirt().empty()
&& extruder_id == layer_tools.extruders.front()) {
const PrintObject *print_object = layers.front().object();
this->set_origin(unscale(print_object->copies()[single_object_idx]));
if (this->m_layer != nullptr && this->m_layer->id() < m_config.skirt_height) {
for (const ExtrusionEntity *ee : print_object->skirt().entities)
gcode += this->extrude_entity(*ee, "skirt", m_config.support_material_speed.value);
}
}
//extrude object-only brim
if (single_object_idx != size_t(-1) && !layers.front().object()->brim().empty() if (single_object_idx != size_t(-1) && !layers.front().object()->brim().empty()
&& extruder_id == layer_tools.extruders.front()) { && extruder_id == layer_tools.extruders.front()) {
const PrintObject *print_object = layers.front().object(); const PrintObject *print_object = layers.front().object();
this->set_origin(unscale(print_object->copies()[single_object_idx])); this->set_origin(unscale(print_object->copies()[single_object_idx]));
if (this->m_layer != nullptr && this->m_layer->id() == 0) {
for (const ExtrusionEntity *ee : print_object->skirt().entities) m_avoid_crossing_perimeters.use_external_mp = true;
gcode += this->extrude_entity(*ee, "skirt", m_config.support_material_speed.value); for (const ExtrusionEntity *ee : print_object->brim().entities)
gcode += this->extrude_entity(*ee, "brim", m_config.support_material_speed.value);
m_avoid_crossing_perimeters.use_external_mp = true; m_avoid_crossing_perimeters.use_external_mp = false;
for (const ExtrusionEntity *ee : print_object->brim().entities) m_avoid_crossing_perimeters.disable_once = true;
gcode += this->extrude_entity(*ee, "brim", m_config.support_material_speed.value); }
m_avoid_crossing_perimeters.use_external_mp = false;
m_avoid_crossing_perimeters.disable_once = true;
} }
@ -1696,7 +1710,7 @@ void GCode::process_layer(
if (print_object == nullptr) if (print_object == nullptr)
// This layer is empty for this particular object, it has neither object extrusions nor support extrusions at this print_z. // This layer is empty for this particular object, it has neither object extrusions nor support extrusions at this print_z.
continue; continue;
std::cout << "Writing gcode for layer at " << layers[layer_id].print_z() << ", " << ((this->m_layer_index * 100) / this->m_layer_count) << "%" << std::endl; //std::cout << "Writing gcode for layer at " << layers[layer_id].print_z() << ", " << ((this->m_layer_index * 100) / this->m_layer_count) << "%" << std::endl;
m_config.apply(print_object->config(), true); m_config.apply(print_object->config(), true);
m_layer = layers[layer_id].layer(); m_layer = layers[layer_id].layer();
@ -2808,7 +2822,8 @@ std::string GCode::travel_to(const Point &point, ExtrusionRole role, std::string
// multi-hop travel path inside the configuration space // multi-hop travel path inside the configuration space
if (needs_retraction if (needs_retraction
&& m_config.avoid_crossing_perimeters && m_config.avoid_crossing_perimeters
&& ! m_avoid_crossing_perimeters.disable_once) { && ! m_avoid_crossing_perimeters.disable_once
&& m_avoid_crossing_perimeters.is_init()) {
travel = m_avoid_crossing_perimeters.travel_to(*this, point); travel = m_avoid_crossing_perimeters.travel_to(*this, point);
// check again whether the new travel path still needs a retraction // check again whether the new travel path still needs a retraction

View File

@ -50,6 +50,7 @@ public:
Polyline travel_to(const GCode &gcodegen, const Point &point); Polyline travel_to(const GCode &gcodegen, const Point &point);
bool is_init() { return (use_external_mp || use_external_mp_once) ? m_external_mp.get() != nullptr : m_layer_mp.get() != nullptr; }
private: private:
std::unique_ptr<MotionPlanner> m_external_mp; std::unique_ptr<MotionPlanner> m_external_mp;
std::unique_ptr<MotionPlanner> m_layer_mp; std::unique_ptr<MotionPlanner> m_layer_mp;

View File

@ -7,6 +7,9 @@
#include <utility> // for std::forward #include <utility> // for std::forward
#include <algorithm> #include <algorithm>
#include "libslic3r.h"
#include "Point.hpp"
namespace Slic3r { namespace Slic3r {
/// Handy little spin mutex for the cached meshes. /// Handy little spin mutex for the cached meshes.
@ -239,13 +242,92 @@ template<class C> bool all_of(const C &container)
}); });
} }
template<class X, class Y> inline X ceil_i(X x, Y y) // A shorter C++14 style form of the enable_if metafunction
{ template<bool B, class T>
static_assert(std::is_integral<X>::value && using enable_if_t = typename std::enable_if<B, T>::type;
std::is_integral<Y>::value && sizeof(X) >= sizeof(Y),
"");
return (x % y) ? x / y + 1 : x / y; // /////////////////////////////////////////////////////////////////////////////
// Type safe conversions to and from scaled and unscaled coordinates
// /////////////////////////////////////////////////////////////////////////////
// A meta-predicate which is true for integers wider than or equal to coord_t
template<class I> struct is_scaled_coord
{
static const SLIC3R_CONSTEXPR bool value =
std::is_integral<I>::value &&
std::numeric_limits<I>::digits >=
std::numeric_limits<coord_t>::digits;
};
// Meta predicates for floating, 'scaled coord' and generic arithmetic types
template<class T>
using FloatingOnly = enable_if_t<std::is_floating_point<T>::value, T>;
template<class T>
using ScaledCoordOnly = enable_if_t<is_scaled_coord<T>::value, T>;
template<class T>
using ArithmeticOnly = enable_if_t<std::is_arithmetic<T>::value, T>;
// A shorter form for a generic Eigen vector which is widely used in PrusaSlicer
template<class T, int N>
using EigenVec = Eigen::Matrix<T, N, 1, Eigen::DontAlign>;
// Semantics are the following:
// Upscaling (scaled()): only from floating point types (or Vec) to either
// floating point or integer 'scaled coord' coordinates.
// Downscaling (unscaled()): from arithmetic types (or Vec) to either
// floating point only
// Conversion definition from unscaled to floating point scaled
template<class Tout,
class Tin,
class = FloatingOnly<Tin>,
class = FloatingOnly<Tout>>
inline SLIC3R_CONSTEXPR Tout scaled(const Tin &v) SLIC3R_NOEXCEPT
{
return static_cast<Tout>(v / static_cast<Tin>(SCALING_FACTOR));
}
// Conversion definition from unscaled to integer 'scaled coord'.
// TODO: is the rounding necessary ? Here it is to show that it can be different
// but it does not have to be. Using std::round means loosing noexcept and
// constexpr modifiers
template<class Tout = coord_t, class Tin, class = FloatingOnly<Tin>>
inline SLIC3R_CONSTEXPR ScaledCoordOnly<Tout> scaled(const Tin &v) SLIC3R_NOEXCEPT
{
//return static_cast<Tout>(std::round(v / SCALING_FACTOR));
return static_cast<Tout>(v / static_cast<Tin>(SCALING_FACTOR));
}
// Conversion for Eigen vectors (N dimensional points)
template<class Tout = coord_t, class Tin, int N, class = FloatingOnly<Tin>>
inline EigenVec<ArithmeticOnly<Tout>, N> scaled(const EigenVec<Tin, N> &v)
{
return v.template cast<Tout>() / SCALING_FACTOR;
}
// Conversion from arithmetic scaled type to floating point unscaled
template<class Tout = double,
class Tin,
class = ArithmeticOnly<Tin>,
class = FloatingOnly<Tout>>
inline SLIC3R_CONSTEXPR Tout unscaled(const Tin &v) SLIC3R_NOEXCEPT
{
return static_cast<Tout>(v * static_cast<Tout>(SCALING_FACTOR));
}
// Unscaling for Eigen vectors. Input base type can be arithmetic, output base
// type can only be floating point.
template<class Tout = double,
class Tin,
int N,
class = ArithmeticOnly<Tin>,
class = FloatingOnly<Tout>>
inline SLIC3R_CONSTEXPR EigenVec<Tout, N> unscaled(
const EigenVec<Tin, N> &v) SLIC3R_NOEXCEPT
{
return v.template cast<Tout>() * SCALING_FACTOR;
} }
} // namespace Slic3r } // namespace Slic3r

View File

@ -13,6 +13,7 @@
#include <list> #include <list>
namespace Slic3r { namespace Slic3r {
int count_error = 0;
void void
MedialAxis::build(Polylines &polylines) MedialAxis::build(Polylines &polylines)
@ -663,11 +664,26 @@ MedialAxis::extends_line(ThickPolyline& polyline, const ExPolygons& anchors, con
if (!finded) { if (!finded) {
if (!this->expolygon.contains(line.b)) { if (!this->expolygon.contains(line.b)) {
//it's outside!!! //it's outside!!!
if (!this->expolygon.contains(line.a)) { //if (!this->expolygon.contains(line.a)) {
std::cout << "Error, a line is formed that start outside a polygon, end outside of it and don't cross it!\n"; // std::cout << "Error, a line is formed that start outside a polygon, end outside of it and don't cross it!\n";
} else { //} else {
std::cout << "Error, a line is formed that start in a polygon, end outside of it and don't cross it!\n"; // std::cout << "Error, a line is formed that start in a polygon, end outside of it and don't cross it!\n";
} //}
//{
// std::stringstream stri;
// stri << "Error_" << (count_error++) << ".svg";
// SVG svg(stri.str());
// svg.draw(anchors);
// svg.draw(this->expolygon);
// svg.draw(line);
// svg.draw(polyline);
// svg.Close();
//}
//it's not possible to print that
polyline.points.clear();
polyline.width.clear();
return;
} }
new_back = line.b; new_back = line.b;
} }

View File

@ -39,7 +39,7 @@ template<> inline Slic3r::Points& contour(Slic3r::Polygon& sh) { return sh.point
template<> inline const Slic3r::Points& contour(const Slic3r::Polygon& sh) { return sh.points; } template<> inline const Slic3r::Points& contour(const Slic3r::Polygon& sh) { return sh.points; }
template<> Slic3r::Points::iterator begin(Slic3r::Points& pts, const PathTag&) { return pts.begin();} template<> Slic3r::Points::iterator begin(Slic3r::Points& pts, const PathTag&) { return pts.begin();}
template<> Slic3r::Points::const_iterator cbegin(const Slic3r::Points& pts, const PathTag&) { return pts.begin(); } template<> Slic3r::Points::const_iterator cbegin(const Slic3r::Points& pts, const PathTag&) { return pts.cbegin(); }
template<> Slic3r::Points::iterator end(Slic3r::Points& pts, const PathTag&) { return pts.end();} template<> Slic3r::Points::iterator end(Slic3r::Points& pts, const PathTag&) { return pts.end();}
template<> Slic3r::Points::const_iterator cend(const Slic3r::Points& pts, const PathTag&) { return pts.cend(); } template<> Slic3r::Points::const_iterator cend(const Slic3r::Points& pts, const PathTag&) { return pts.cend(); }
@ -71,56 +71,61 @@ using Rational = boost::rational<__int128>;
MinAreaBoundigBox::MinAreaBoundigBox(const Polygon &p, PolygonLevel pc) MinAreaBoundigBox::MinAreaBoundigBox(const Polygon &p, PolygonLevel pc)
{ {
const Polygon& chull = pc == pcConvex ? p : libnest2d::sl::convexHull(p); const Polygon &chull = pc == pcConvex ? p :
libnest2d::sl::convexHull(p);
libnest2d::RotatedBox<Point, Unit> box = libnest2d::RotatedBox<Point, Unit> box =
libnest2d::minAreaBoundingBox<Polygon, Unit, Rational>(chull); libnest2d::minAreaBoundingBox<Polygon, Unit, Rational>(chull);
m_right = box.right_extent(); m_right = libnest2d::cast<long double>(box.right_extent());
m_bottom = box.bottom_extent(); m_bottom = libnest2d::cast<long double>(box.bottom_extent());
m_axis = box.axis(); m_axis = box.axis();
} }
MinAreaBoundigBox::MinAreaBoundigBox(const ExPolygon &p, PolygonLevel pc) MinAreaBoundigBox::MinAreaBoundigBox(const ExPolygon &p, PolygonLevel pc)
{ {
const ExPolygon& chull = pc == pcConvex ? p : libnest2d::sl::convexHull(p); const ExPolygon &chull = pc == pcConvex ? p :
libnest2d::sl::convexHull(p);
libnest2d::RotatedBox<Point, Unit> box = libnest2d::RotatedBox<Point, Unit> box =
libnest2d::minAreaBoundingBox<ExPolygon, Unit, Rational>(chull); libnest2d::minAreaBoundingBox<ExPolygon, Unit, Rational>(chull);
m_right = box.right_extent(); m_right = libnest2d::cast<long double>(box.right_extent());
m_bottom = box.bottom_extent(); m_bottom = libnest2d::cast<long double>(box.bottom_extent());
m_axis = box.axis(); m_axis = box.axis();
} }
MinAreaBoundigBox::MinAreaBoundigBox(const Points &pts, PolygonLevel pc) MinAreaBoundigBox::MinAreaBoundigBox(const Points &pts, PolygonLevel pc)
{ {
const Points& chull = pc == pcConvex ? pts : libnest2d::sl::convexHull(pts); const Points &chull = pc == pcConvex ? pts :
libnest2d::sl::convexHull(pts);
libnest2d::RotatedBox<Point, Unit> box = libnest2d::RotatedBox<Point, Unit> box =
libnest2d::minAreaBoundingBox<Points, Unit, Rational>(chull); libnest2d::minAreaBoundingBox<Points, Unit, Rational>(chull);
m_right = box.right_extent(); m_right = libnest2d::cast<long double>(box.right_extent());
m_bottom = box.bottom_extent(); m_bottom = libnest2d::cast<long double>(box.bottom_extent());
m_axis = box.axis(); m_axis = box.axis();
} }
double MinAreaBoundigBox::angle_to_X() const double MinAreaBoundigBox::angle_to_X() const
{ {
double ret = std::atan2(m_axis.y(), m_axis.x()); double ret = std::atan2(m_axis.y(), m_axis.x());
auto s = std::signbit(ret); auto s = std::signbit(ret);
if(s) ret += 2 * PI; if (s) ret += 2 * PI;
return -ret; return -ret;
} }
long double MinAreaBoundigBox::width() const long double MinAreaBoundigBox::width() const
{ {
return std::abs(m_bottom) / std::sqrt(libnest2d::pl::magnsq<Point, long double>(m_axis)); return std::abs(m_bottom) /
std::sqrt(libnest2d::pl::magnsq<Point, long double>(m_axis));
} }
long double MinAreaBoundigBox::height() const long double MinAreaBoundigBox::height() const
{ {
return std::abs(m_right) / std::sqrt(libnest2d::pl::magnsq<Point, long double>(m_axis)); return std::abs(m_right) /
std::sqrt(libnest2d::pl::magnsq<Point, long double>(m_axis));
} }
long double MinAreaBoundigBox::area() const long double MinAreaBoundigBox::area() const
@ -138,5 +143,4 @@ void remove_collinear_points(ExPolygon &p)
{ {
p = libnest2d::removeCollinearPoints<ExPolygon>(p, Unit(0)); p = libnest2d::removeCollinearPoints<ExPolygon>(p, Unit(0));
} }
} // namespace Slic3r
}

View File

@ -1564,8 +1564,10 @@ void ModelVolume::center_geometry_after_creation()
Vec3d shift = this->mesh().bounding_box().center(); Vec3d shift = this->mesh().bounding_box().center();
if (!shift.isApprox(Vec3d::Zero())) if (!shift.isApprox(Vec3d::Zero()))
{ {
m_mesh->translate(-(float)shift(0), -(float)shift(1), -(float)shift(2)); if (m_mesh)
m_convex_hull->translate(-(float)shift(0), -(float)shift(1), -(float)shift(2)); m_mesh->translate(-(float)shift(0), -(float)shift(1), -(float)shift(2));
if (m_convex_hull)
m_convex_hull->translate(-(float)shift(0), -(float)shift(1), -(float)shift(2));
translate(shift); translate(shift);
} }
} }

View File

@ -63,9 +63,9 @@ std::string toString(const Model& model, bool holes = true) {
ExPolygons expolys = tmpmesh.horizontal_projection(); ExPolygons expolys = tmpmesh.horizontal_projection();
for(auto& expoly_complex : expolys) { for(auto& expoly_complex : expolys) {
auto tmp = expoly_complex.simplify(1.0/SCALING_FACTOR); ExPolygons tmp = expoly_complex.simplify(scaled<double>(1.));
if(tmp.empty()) continue; if(tmp.empty()) continue;
auto expoly = tmp.front(); ExPolygon expoly = tmp.front();
expoly.contour.make_clockwise(); expoly.contour.make_clockwise();
for(auto& h : expoly.holes) h.make_counter_clockwise(); for(auto& h : expoly.holes) h.make_counter_clockwise();
@ -610,7 +610,7 @@ ShapeData2D projectModelFromTop(const Slic3r::Model &model,
if(tolerance > EPSILON) { if(tolerance > EPSILON) {
Polygons pp { p }; Polygons pp { p };
pp = p.simplify(double(scaled(tolerance))); pp = p.simplify(scaled<double>(tolerance));
if (!pp.empty()) p = pp.front(); if (!pp.empty()) p = pp.front();
} }
@ -633,8 +633,8 @@ ShapeData2D projectModelFromTop(const Slic3r::Model &model,
if(item.vertexCount() > 3) { if(item.vertexCount() > 3) {
item.rotation(Geometry::rotation_diff_z(rotation0, objinst->get_rotation())); item.rotation(Geometry::rotation_diff_z(rotation0, objinst->get_rotation()));
item.translation({ item.translation({
ClipperLib::cInt(objinst->get_offset(X)/SCALING_FACTOR), scaled<ClipperLib::cInt>(objinst->get_offset(X)),
ClipperLib::cInt(objinst->get_offset(Y)/SCALING_FACTOR) scaled<ClipperLib::cInt>(objinst->get_offset(Y))
}); });
ret.emplace_back(objinst, item); ret.emplace_back(objinst, item);
} }
@ -658,8 +658,8 @@ ShapeData2D projectModelFromTop(const Slic3r::Model &model,
Item item(std::move(pn)); Item item(std::move(pn));
item.rotation(wti.rotation), item.rotation(wti.rotation),
item.translation({ item.translation({
ClipperLib::cInt(wti.pos(0)/SCALING_FACTOR), scaled<ClipperLib::cInt>(wti.pos(0)),
ClipperLib::cInt(wti.pos(1)/SCALING_FACTOR) scaled<ClipperLib::cInt>(wti.pos(1))
}); });
ret.emplace_back(nullptr, item); ret.emplace_back(nullptr, item);
} }
@ -822,7 +822,9 @@ bool arrange(Model &model, // The model with the geometries
auto& cfn = stopcondition; auto& cfn = stopcondition;
coord_t md = ceil_i(min_obj_distance, 2) - SCALED_EPSILON; // Integer ceiling the min distance from the bed perimeters
coord_t md = min_obj_distance - SCALED_EPSILON;
md = (md % 2) ? md / 2 + 1 : md / 2;
auto binbb = Box({libnest2d::Coord{bbb.min(0)} - md, auto binbb = Box({libnest2d::Coord{bbb.min(0)} - md,
libnest2d::Coord{bbb.min(1)} - md}, libnest2d::Coord{bbb.min(1)} - md},
@ -916,7 +918,9 @@ void find_new_position(const Model &model,
BoundingBox bbb(bed); BoundingBox bbb(bed);
coord_t md = ceil_i(min_obj_distance, 2) - SCALED_EPSILON; // Integer ceiling the min distance from the bed perimeters
coord_t md = min_obj_distance - SCALED_EPSILON;
md = (md % 2) ? md / 2 + 1 : md / 2;
auto binbb = Box({libnest2d::Coord{bbb.min(0)} - md, auto binbb = Box({libnest2d::Coord{bbb.min(0)} - md,
libnest2d::Coord{bbb.min(1)} - md}, libnest2d::Coord{bbb.min(1)} - md},

View File

@ -201,7 +201,9 @@ bool Print::invalidate_state_by_config_options(const std::vector<t_config_option
|| opt_key == "min_skirt_length" || opt_key == "min_skirt_length"
|| opt_key == "ooze_prevention") { || opt_key == "ooze_prevention") {
steps.emplace_back(psSkirt); steps.emplace_back(psSkirt);
} else if (opt_key == "brim_width" } else if (
opt_key == "complete_objects"
|| opt_key == "brim_width"
|| opt_key == "brim_ears" || opt_key == "brim_ears"
|| opt_key == "brim_ears_max_angle") { || opt_key == "brim_ears_max_angle") {
steps.emplace_back(psBrim); steps.emplace_back(psBrim);
@ -211,8 +213,7 @@ bool Print::invalidate_state_by_config_options(const std::vector<t_config_option
|| opt_key == "resolution") { || opt_key == "resolution") {
osteps.emplace_back(posSlice); osteps.emplace_back(posSlice);
} else if ( } else if (
opt_key == "complete_objects" opt_key == "filament_type"
|| opt_key == "filament_type"
|| opt_key == "filament_soluble" || opt_key == "filament_soluble"
|| opt_key == "first_layer_temperature" || opt_key == "first_layer_temperature"
|| opt_key == "filament_loading_speed" || opt_key == "filament_loading_speed"
@ -1513,12 +1514,15 @@ void Print::process()
obj->generate_support_material(); obj->generate_support_material();
if (this->set_started(psSkirt)) { if (this->set_started(psSkirt)) {
m_skirt.clear(); m_skirt.clear();
for (PrintObject *obj : m_objects) {
obj->m_skirt.clear();
}
if (this->has_skirt()) { if (this->has_skirt()) {
this->set_status(88, L("Generating skirt")); this->set_status(88, L("Generating skirt"));
if (config().complete_objects){ if (config().complete_objects){
for (PrintObject *obj : m_objects){ for (PrintObject *obj : m_objects){
//create a skirt "pattern" (one per object) //create a skirt "pattern" (one per object)
const Points copies = obj->copies(); const Points copies{ obj->copies() };
obj->m_copies.clear(); obj->m_copies.clear();
obj->m_copies.emplace_back(); obj->m_copies.emplace_back();
this->_make_skirt({ obj }, obj->m_skirt); this->_make_skirt({ obj }, obj->m_skirt);
@ -1532,6 +1536,9 @@ void Print::process()
} }
if (this->set_started(psBrim)) { if (this->set_started(psBrim)) {
m_brim.clear(); m_brim.clear();
for (PrintObject *obj : m_objects) {
obj->m_brim.clear();
}
if (m_config.brim_width > 0) { if (m_config.brim_width > 0) {
this->set_status(88, L("Generating brim")); this->set_status(88, L("Generating brim"));
if (config().complete_objects){ if (config().complete_objects){

View File

@ -5,6 +5,7 @@
#include "SLABoostAdapter.hpp" #include "SLABoostAdapter.hpp"
#include "ClipperUtils.hpp" #include "ClipperUtils.hpp"
#include "Tesselate.hpp" #include "Tesselate.hpp"
#include "MTUtils.hpp"
// For debugging: // For debugging:
//#include <fstream> //#include <fstream>
@ -203,7 +204,7 @@ void offset(ExPolygon& sh, coord_t distance) {
} }
ClipperOffset offs; ClipperOffset offs;
offs.ArcTolerance = 0.01*scaled(1.0); offs.ArcTolerance = scaled<double>(0.01);
Paths result; Paths result;
offs.AddPath(ctour, jtRound, etClosedPolygon); offs.AddPath(ctour, jtRound, etClosedPolygon);
offs.AddPaths(holes, jtRound, etClosedPolygon); offs.AddPaths(holes, jtRound, etClosedPolygon);
@ -351,7 +352,7 @@ Contour3D round_edges(const ExPolygon& base_plate,
double x2 = xx*xx; double x2 = xx*xx;
double stepy = std::sqrt(r2 - x2); double stepy = std::sqrt(r2 - x2);
offset(ob, s*scaled(xx)); offset(ob, s * scaled(xx));
wh = ceilheight_mm - radius_mm + stepy; wh = ceilheight_mm - radius_mm + stepy;
Contour3D pwalls; Contour3D pwalls;
@ -375,7 +376,7 @@ Contour3D round_edges(const ExPolygon& base_plate,
double xx = radius_mm - i*stepx; double xx = radius_mm - i*stepx;
double x2 = xx*xx; double x2 = xx*xx;
double stepy = std::sqrt(r2 - x2); double stepy = std::sqrt(r2 - x2);
offset(ob, s*scaled(xx)); offset(ob, s * scaled(xx));
wh = ceilheight_mm - radius_mm - stepy; wh = ceilheight_mm - radius_mm - stepy;
Contour3D pwalls; Contour3D pwalls;
@ -476,7 +477,7 @@ ExPolygons concave_hull(const ExPolygons& polys, double max_dist_mm = 50,
double dx = x(c) - x(cc), dy = y(c) - y(cc); double dx = x(c) - x(cc), dy = y(c) - y(cc);
double l = std::sqrt(dx * dx + dy * dy); double l = std::sqrt(dx * dx + dy * dy);
double nx = dx / l, ny = dy / l; double nx = dx / l, ny = dy / l;
double max_dist = scaled(max_dist_mm); double max_dist = scaled<double>(max_dist_mm);
ExPolygon& expo = punion[idx++]; ExPolygon& expo = punion[idx++];
BoundingBox querybb(expo); BoundingBox querybb(expo);
@ -492,7 +493,7 @@ ExPolygons concave_hull(const ExPolygons& polys, double max_dist_mm = 50,
ctour.reserve(3); ctour.reserve(3);
ctour.emplace_back(cc); ctour.emplace_back(cc);
Point d(coord_t(scaled(1.)*nx), coord_t(scaled(1.)*ny)); Point d(scaled(nx), scaled(ny));
ctour.emplace_back(c + Point( -y(d), x(d) )); ctour.emplace_back(c + Point( -y(d), x(d) ));
ctour.emplace_back(c + Point( y(d), -x(d) )); ctour.emplace_back(c + Point( y(d), -x(d) ));
offset(r, scaled(1.)); offset(r, scaled(1.));
@ -529,14 +530,14 @@ void base_plate(const TriangleMesh &mesh, ExPolygons &output, float h,
ExPolygons tmp; tmp.reserve(count); ExPolygons tmp; tmp.reserve(count);
for(ExPolygons& o : out) for(ExPolygons& o : out)
for(ExPolygon& e : o) { for(ExPolygon& e : o) {
auto&& exss = e.simplify(scaled(0.1)); auto&& exss = e.simplify(scaled<double>(0.1));
for(ExPolygon& ep : exss) tmp.emplace_back(std::move(ep)); for(ExPolygon& ep : exss) tmp.emplace_back(std::move(ep));
} }
ExPolygons utmp = unify(tmp); ExPolygons utmp = unify(tmp);
for(auto& o : utmp) { for(auto& o : utmp) {
auto&& smp = o.simplify(scaled(0.1)); auto&& smp = o.simplify(scaled<double>(0.1));
output.insert(output.end(), smp.begin(), smp.end()); output.insert(output.end(), smp.begin(), smp.end());
} }
} }

View File

@ -668,7 +668,7 @@ void SLAPrint::process()
double ilhd = m_material_config.initial_layer_height.getFloat(); double ilhd = m_material_config.initial_layer_height.getFloat();
auto ilh = float(ilhd); auto ilh = float(ilhd);
auto ilhs = scaled(ilhd); coord_t ilhs = scaled(ilhd);
const size_t objcount = m_objects.size(); const size_t objcount = m_objects.size();
static const unsigned min_objstatus = 0; // where the per object operations start static const unsigned min_objstatus = 0; // where the per object operations start
@ -694,17 +694,15 @@ void SLAPrint::process()
// We need to prepare the slice index... // We need to prepare the slice index...
double lhd = m_objects.front()->m_config.layer_height.getFloat(); double lhd = m_objects.front()->m_config.layer_height.getFloat();
float lh = float(lhd); float lh = float(lhd);
auto lhs = scaled(lhd); coord_t lhs = scaled(lhd);
auto && bb3d = mesh.bounding_box();
auto &&bb3d = mesh.bounding_box(); double minZ = bb3d.min(Z) - po.get_elevation();
double minZ = bb3d.min(Z) - po.get_elevation(); double maxZ = bb3d.max(Z);
double maxZ = bb3d.max(Z); auto minZf = float(minZ);
auto minZf = float(minZ); coord_t minZs = scaled(minZ);
coord_t maxZs = scaled(maxZ);
auto minZs = scaled(minZ);
auto maxZs = scaled(maxZ);
po.m_slice_index.clear(); po.m_slice_index.clear();
@ -722,8 +720,9 @@ void SLAPrint::process()
if(slindex_it == po.m_slice_index.end()) if(slindex_it == po.m_slice_index.end())
//TRN To be shown at the status bar on SLA slicing error. //TRN To be shown at the status bar on SLA slicing error.
throw std::runtime_error(L("Slicing had to be stopped " throw std::runtime_error(
"due to an internal error.")); L("Slicing had to be stopped due to an internal error: "
"Inconsistent slice index."));
po.m_model_height_levels.clear(); po.m_model_height_levels.clear();
po.m_model_height_levels.reserve(po.m_slice_index.size()); po.m_model_height_levels.reserve(po.m_slice_index.size());
@ -1013,9 +1012,6 @@ void SLAPrint::process()
using ClipperPolygons = std::vector<ClipperPolygon>; using ClipperPolygons = std::vector<ClipperPolygon>;
namespace sl = libnest2d::shapelike; // For algorithms namespace sl = libnest2d::shapelike; // For algorithms
// If the raster has vertical orientation, we will flip the coordinates
// bool flpXY = m_printer_config.display_orientation.getInt() == SLADisplayOrientation::sladoPortrait;
// Set up custom union and diff functions for clipper polygons // Set up custom union and diff functions for clipper polygons
auto polyunion = [] (const ClipperPolygons& subjects) auto polyunion = [] (const ClipperPolygons& subjects)
{ {
@ -1066,8 +1062,8 @@ void SLAPrint::process()
const int fade_layers_cnt = m_default_object_config.faded_layers.getInt();// 10 // [3;20] const int fade_layers_cnt = m_default_object_config.faded_layers.getInt();// 10 // [3;20]
const double width = scaled(m_printer_config.display_width.getFloat()); const auto width = scaled<double>(m_printer_config.display_width.getFloat());
const double height = scaled(m_printer_config.display_height.getFloat()); const auto height = scaled<double>(m_printer_config.display_height.getFloat());
const double display_area = width*height; const double display_area = width*height;
// get polygons for all instances in the object // get polygons for all instances in the object
@ -1123,11 +1119,6 @@ void SLAPrint::process()
sl::translate(poly, ClipperPoint{instances[i].shift(X), sl::translate(poly, ClipperPoint{instances[i].shift(X),
instances[i].shift(Y)}); instances[i].shift(Y)});
// if (flpXY) {
// for(auto& p : poly.Contour) std::swap(p.X, p.Y);
// for(auto& h : poly.Holes) for(auto& p : h) std::swap(p.X, p.Y);
// }
polygons.emplace_back(std::move(poly)); polygons.emplace_back(std::move(poly));
} }
} }

View File

@ -15,6 +15,8 @@
#define ENABLE_RENDER_STATISTICS 0 #define ENABLE_RENDER_STATISTICS 0
// Shows an imgui dialog with camera related data // Shows an imgui dialog with camera related data
#define ENABLE_CAMERA_STATISTICS 0 #define ENABLE_CAMERA_STATISTICS 0
// Render the picking pass instead of the main scene (use [T] key to toggle between regular rendering and picking pass only rendering)
#define ENABLE_RENDER_PICKING_PASS 0
//==================== //====================
@ -48,5 +50,5 @@
#define ENABLE_SVG_ICONS (1 && ENABLE_1_42_0_ALPHA8 && ENABLE_TEXTURES_FROM_SVG) #define ENABLE_SVG_ICONS (1 && ENABLE_1_42_0_ALPHA8 && ENABLE_TEXTURES_FROM_SVG)
#define DEBUG_EXTRUSION_OUTPUT 0 //#define DEBUG_EXTRUSION_OUTPUT 0
#endif // _technologies_h_ #endif // _technologies_h_

View File

@ -547,9 +547,9 @@ TriangleMesh TriangleMesh::convex_hull_3d() const
#if REALfloat #if REALfloat
qhull.runQhull("", 3, (int)this->its.vertices.size(), (const realT*)(this->its.vertices.front().data()), "Qt"); qhull.runQhull("", 3, (int)this->its.vertices.size(), (const realT*)(this->its.vertices.front().data()), "Qt");
#else #else
src_vertices.reserve(this->its.vertices() * 3); src_vertices.reserve(this->its.vertices.size() * 3);
// We will now fill the vector with input points for computation: // We will now fill the vector with input points for computation:
for (const stl_vertex &v : ths->its.vertices.size()) for (const stl_vertex &v : this->its.vertices)
for (int i = 0; i < 3; ++ i) for (int i = 0; i < 3; ++ i)
src_vertices.emplace_back(v(i)); src_vertices.emplace_back(v(i));
qhull.runQhull("", 3, (int)src_vertices.size() / 3, src_vertices.data(), "Qt"); qhull.runQhull("", 3, (int)src_vertices.size() / 3, src_vertices.data(), "Qt");

View File

@ -167,7 +167,7 @@ template<class T> size_t next_highest_power_of_2(T v,
extern std::string xml_escape(std::string text); extern std::string xml_escape(std::string text);
#if defined __GNUC__ & __GNUC__ < 5 #if defined __GNUC__ && __GNUC__ < 5 && !defined __clang__
// Older GCCs don't have std::is_trivially_copyable // Older GCCs don't have std::is_trivially_copyable
// cf. https://gcc.gnu.org/onlinedocs/gcc-4.9.4/libstdc++/manual/manual/status.html#status.iso.2011 // cf. https://gcc.gnu.org/onlinedocs/gcc-4.9.4/libstdc++/manual/manual/status.html#status.iso.2011
#warning "GCC version < 5, faking std::is_trivially_copyable" #warning "GCC version < 5, faking std::is_trivially_copyable"

View File

@ -60,20 +60,6 @@ typedef double coordf_t;
#define SLIC3R_NOEXCEPT noexcept #define SLIC3R_NOEXCEPT noexcept
#endif #endif
template<class Tf> inline SLIC3R_CONSTEXPR coord_t scaled(Tf val)
{
static_assert (std::is_floating_point<Tf>::value, "Floating point only");
return coord_t(val / Tf(SCALING_FACTOR));
}
template<class Tf = double> inline SLIC3R_CONSTEXPR Tf unscaled(coord_t val)
{
static_assert (std::is_floating_point<Tf>::value, "Floating point only");
return Tf(val * Tf(SCALING_FACTOR));
}
inline SLIC3R_CONSTEXPR float unscaledf(coord_t val) { return unscaled<float>(val); }
inline std::string debug_out_path(const char *name, ...) inline std::string debug_out_path(const char *name, ...)
{ {
char buffer[2048]; char buffer[2048];

View File

@ -22,6 +22,10 @@
static const size_t MAX_SIZE = sizeof(char) * 255; static const size_t MAX_SIZE = sizeof(char) * 255;
static const int MAX_SAFE_INT = (unsigned int) -1 >> 1; static const int MAX_SAFE_INT = (unsigned int) -1 >> 1;
#ifdef _WIN32
#define strdup _strdup
#endif
/** /**
* Define comparison operators, storing the * Define comparison operators, storing the
* ASCII code per each symbol in hexadecimal notation. * ASCII code per each symbol in hexadecimal notation.
@ -50,8 +54,8 @@ strcut (char *str, int begin, int len) {
if((int)l < 0 || (int)l > MAX_SAFE_INT) return -1; if((int)l < 0 || (int)l > MAX_SAFE_INT) return -1;
if (len < 0) len = l - begin + 1; if (len < 0) len = (int)l - begin + 1;
if (begin + len > (int)l) len = l - begin; if (begin + len > (int)l) len = (int)l - begin;
memmove(str + begin, str + begin + len, l - len + 1 - begin); memmove(str + begin, str + begin + len, l - len + 1 - begin);
return len; return len;
@ -104,7 +108,7 @@ parse_int (const char *s) {
static char * static char *
parse_slice (char *buf, char sep) { parse_slice (char *buf, char sep) {
char *pr, *part; char *pr, *part;
int plen; size_t plen;
/* Find separator in buf */ /* Find separator in buf */
pr = strchr(buf, sep); pr = strchr(buf, sep);
@ -210,8 +214,9 @@ semver_parse_version (const char *str, semver_t *ver) {
static int static int
compare_prerelease (char *x, char *y) { compare_prerelease (char *x, char *y) {
char *lastx, *lasty, *xptr, *yptr, *endptr; char *lastx, *lasty, *xptr, *yptr, *endptr;
int xlen, ylen, xisnum, yisnum, xnum, ynum; size_t xlen, ylen, xn, yn, min;
int xn, yn, min, res; int xisnum, yisnum, xnum, ynum;
int res;
if (x == NULL && y == NULL) return 0; if (x == NULL && y == NULL) return 0;
if (y == NULL && x) return -1; if (y == NULL && x) return -1;
if (x == NULL && y) return 1; if (x == NULL && y) return 1;
@ -572,7 +577,7 @@ semver_clean (char *s) {
for (i = 0; i < len; i++) { for (i = 0; i < len; i++) {
if (contains(s[i], VALID_CHARS, mlen) == 0) { if (contains(s[i], VALID_CHARS, mlen) == 0) {
res = strcut(s, i, 1); res = strcut(s, (int)i, 1);
if(res == -1) return -1; if(res == -1) return -1;
--len; --i; --len; --i;
} }

View File

@ -44,8 +44,8 @@ public:
const float* get_vertices_data() const; const float* get_vertices_data() const;
unsigned int get_vertices_data_size() const { return (unsigned int)m_vertices.size() * get_vertex_data_size(); } unsigned int get_vertices_data_size() const { return (unsigned int)m_vertices.size() * get_vertex_data_size(); }
unsigned int get_vertex_data_size() const { return (unsigned int)(5 * sizeof(float)); } unsigned int get_vertex_data_size() const { return (unsigned int)(5 * sizeof(float)); }
unsigned int get_position_offset() const { return 0; } size_t get_position_offset() const { return 0; }
unsigned int get_tex_coords_offset() const { return (unsigned int)(3 * sizeof(float)); } size_t get_tex_coords_offset() const { return (size_t)(3 * sizeof(float)); }
unsigned int get_vertices_count() const { return (unsigned int)m_vertices.size(); } unsigned int get_vertices_count() const { return (unsigned int)m_vertices.size(); }
#else #else
const float* get_vertices() const { return m_vertices.data(); } const float* get_vertices() const { return m_vertices.data(); }

View File

@ -1670,7 +1670,8 @@ void ExtrusionToVert::use(const ExtrusionEntityCollection &collection) { for (co
void _3DScene::extrusionentity_to_verts(const ExtrusionEntity &extrusion_entity, float print_z, const Point &copy, GLVolume &volume) void _3DScene::extrusionentity_to_verts(const ExtrusionEntity &extrusion_entity, float print_z, const Point &copy, GLVolume &volume)
{ {
extrusion_entity.visit(ExtrusionToVert(print_z, copy, volume)); ExtrusionToVert visitor(print_z, copy, volume);
extrusion_entity.visit(visitor);
} }
void _3DScene::polyline3_to_verts(const Polyline3& polyline, double width, double height, GLVolume& volume) void _3DScene::polyline3_to_verts(const Polyline3& polyline, double width, double height, GLVolume& volume)

View File

@ -53,15 +53,12 @@ void BedShapeDialog::on_dpi_changed(const wxRect &suggested_rect)
void BedShapePanel::build_panel(ConfigOptionPoints* default_pt) void BedShapePanel::build_panel(ConfigOptionPoints* default_pt)
{ {
// on_change(nullptr); auto sbsizer = new wxStaticBoxSizer(wxVERTICAL, this, _(L("Shape")));
auto box = new wxStaticBox(this, wxID_ANY, _(L("Shape")));
auto sbsizer = new wxStaticBoxSizer(box, wxVERTICAL);
// shape options // shape options
m_shape_options_book = new wxChoicebook(this, wxID_ANY, wxDefaultPosition, m_shape_options_book = new wxChoicebook(this, wxID_ANY, wxDefaultPosition,
wxSize(25*wxGetApp().em_unit(), -1), wxCHB_TOP); wxSize(25*wxGetApp().em_unit(), -1), wxCHB_TOP);
sbsizer->Add(m_shape_options_book); sbsizer->Add(m_shape_options_book);
auto optgroup = init_shape_options_page(_(L("Rectangular"))); auto optgroup = init_shape_options_page(_(L("Rectangular")));
ConfigOptionDef def; ConfigOptionDef def;
@ -92,13 +89,15 @@ void BedShapePanel::build_panel(ConfigOptionPoints* default_pt)
Line line{ "", "" }; Line line{ "", "" };
line.full_width = 1; line.full_width = 1;
line.widget = [this](wxWindow* parent) { line.widget = [this](wxWindow* parent) {
auto btn = new wxButton(parent, wxID_ANY, _(L("Load shape from STL...")), wxDefaultPosition, wxDefaultSize); auto shape_btn = new wxButton(parent, wxID_ANY, _(L("Load shape from STL...")));
wxSizer* shape_sizer = new wxBoxSizer(wxHORIZONTAL);
shape_sizer->Add(shape_btn, 1, wxEXPAND);
auto sizer = new wxBoxSizer(wxHORIZONTAL); wxSizer* sizer = new wxBoxSizer(wxVERTICAL);
sizer->Add(btn); sizer->Add(shape_sizer, 1, wxEXPAND);
btn->Bind(wxEVT_BUTTON, ([this](wxCommandEvent e) shape_btn->Bind(wxEVT_BUTTON, ([this](wxCommandEvent& e)
{ {
load_stl(); load_stl();
})); }));
@ -106,8 +105,8 @@ void BedShapePanel::build_panel(ConfigOptionPoints* default_pt)
}; };
optgroup->append_line(line); optgroup->append_line(line);
Bind(wxEVT_CHOICEBOOK_PAGE_CHANGED, ([this](wxCommandEvent e) Bind(wxEVT_CHOICEBOOK_PAGE_CHANGED, ([this](wxCommandEvent& e)
{ {
update_shape(); update_shape();
})); }));
@ -117,8 +116,8 @@ void BedShapePanel::build_panel(ConfigOptionPoints* default_pt)
// main sizer // main sizer
auto top_sizer = new wxBoxSizer(wxHORIZONTAL); auto top_sizer = new wxBoxSizer(wxHORIZONTAL);
top_sizer->Add(sbsizer, 0, wxEXPAND | wxLeft | wxTOP | wxBOTTOM, 10); top_sizer->Add(sbsizer, 0, wxEXPAND | wxLEFT | wxTOP | wxBOTTOM, 10);
if (m_canvas) if (m_canvas)
top_sizer->Add(m_canvas, 1, wxEXPAND | wxALL, 10) ; top_sizer->Add(m_canvas, 1, wxEXPAND | wxALL, 10) ;
SetSizerAndFit(top_sizer); SetSizerAndFit(top_sizer);
@ -135,8 +134,7 @@ void BedShapePanel::build_panel(ConfigOptionPoints* default_pt)
// Create a panel for a rectangular / circular / custom bed shape. // Create a panel for a rectangular / circular / custom bed shape.
ConfigOptionsGroupShp BedShapePanel::init_shape_options_page(const wxString& title) ConfigOptionsGroupShp BedShapePanel::init_shape_options_page(const wxString& title)
{ {
auto panel = new wxPanel(m_shape_options_book);
auto panel = new wxPanel(m_shape_options_book);
ConfigOptionsGroupShp optgroup; ConfigOptionsGroupShp optgroup;
optgroup = std::make_shared<ConfigOptionsGroup>(panel, _(L("Settings"))); optgroup = std::make_shared<ConfigOptionsGroup>(panel, _(L("Settings")));
@ -234,8 +232,8 @@ void BedShapePanel::set_shape(ConfigOptionPoints* points)
// This is a custom bed shape, use the polygon provided. // This is a custom bed shape, use the polygon provided.
m_shape_options_book->SetSelection(SHAPE_CUSTOM); m_shape_options_book->SetSelection(SHAPE_CUSTOM);
// Copy the polygon to the canvas, make a copy of the array. // Copy the polygon to the canvas, make a copy of the array.
m_canvas->m_bed_shape = points->values; m_loaded_bed_shape = points->values;
update_shape(); update_shape();
} }
void BedShapePanel::update_preview() void BedShapePanel::update_preview()

View File

@ -171,7 +171,7 @@ void BonjourDialog::on_reply(BonjourReplyEvent &e)
// Filter replies based on selected technology // Filter replies based on selected technology
const auto model = e.reply.txt_data.find("model"); const auto model = e.reply.txt_data.find("model");
const bool sl1 = model != e.reply.txt_data.end() && model->second == "SL1"; const bool sl1 = model != e.reply.txt_data.end() && model->second == "SL1";
if (tech != ptSLA && sl1 || tech == ptSLA && !sl1) { if ((tech != ptSLA && sl1) || (tech == ptSLA && !sl1)) {
return; return;
} }

View File

@ -24,7 +24,7 @@ namespace GUI {
const double Camera::DefaultDistance = 1000.0; const double Camera::DefaultDistance = 1000.0;
double Camera::FrustrumMinZSize = 50.0; double Camera::FrustrumMinZSize = 50.0;
double Camera::FrustrumZMargin = 10.0; double Camera::FrustrumZMargin = 10.0;
double Camera::FovMinDeg = 5.0; double Camera::FovMinDeg = 0.5;
double Camera::FovMaxDeg = 75.0; double Camera::FovMaxDeg = 75.0;
Camera::Camera() Camera::Camera()

View File

@ -810,7 +810,7 @@ void ConfigWizardIndex::on_paint(wxPaintEvent & evt)
const Item& item = items[i]; const Item& item = items[i];
unsigned x = em_w/2 + item.indent * em_w; unsigned x = em_w/2 + item.indent * em_w;
if (i == item_active || item_hover >= 0 && i == (size_t)item_hover) { if (i == item_active || (item_hover >= 0 && i == (size_t)item_hover)) {
dc.DrawBitmap(bullet_blue.bmp(), x, y + yoff_icon, false); dc.DrawBitmap(bullet_blue.bmp(), x, y + yoff_icon, false);
} }
else if (i < item_active) { dc.DrawBitmap(bullet_black.bmp(), x, y + yoff_icon, false); } else if (i < item_active) { dc.DrawBitmap(bullet_black.bmp(), x, y + yoff_icon, false); }

View File

@ -442,8 +442,7 @@ void FirmwareDialog::priv::avr109_lookup_port(Avr109Pid usb_pid)
auto ports = Utils::scan_serial_ports_extended(); auto ports = Utils::scan_serial_ports_extended();
ports.erase(std::remove_if(ports.begin(), ports.end(), [=](const SerialPortInfo &port ) { ports.erase(std::remove_if(ports.begin(), ports.end(), [=](const SerialPortInfo &port ) {
return port.id_vendor != USB_VID_PRUSA || return port.id_vendor != USB_VID_PRUSA ||
port.id_product != usb_pid.boot && (port.id_product != usb_pid.boot && port.id_product != usb_pid.app);
port.id_product != usb_pid.app;
}), ports.end()); }), ports.end());
if (ports.size() == 0) { if (ports.size() == 0) {

View File

@ -457,8 +457,10 @@ void GLCanvas3D::LayersEditing::_render_profile(const Rect& bar_rect) const
{ {
//FIXME show some kind of legend. //FIXME show some kind of legend.
if (!m_slicing_parameters)
return;
// Make the vertical bar a bit wider so the layer height curve does not touch the edge of the bar region. // Make the vertical bar a bit wider so the layer height curve does not touch the edge of the bar region.
assert(m_slicing_parameters != nullptr);
float scale_x = bar_rect.get_width() / (float)(1.12 * m_slicing_parameters->max_layer_height); float scale_x = bar_rect.get_width() / (float)(1.12 * m_slicing_parameters->max_layer_height);
float scale_y = bar_rect.get_height() / m_object_max_z; float scale_y = bar_rect.get_height() / m_object_max_z;
float x = bar_rect.get_left() + (float)m_slicing_parameters->layer_height * scale_x; float x = bar_rect.get_left() + (float)m_slicing_parameters->layer_height * scale_x;
@ -910,7 +912,8 @@ GLCanvas3D::LegendTexture::LegendTexture()
void GLCanvas3D::LegendTexture::fill_color_print_legend_values(const GCodePreviewData& preview_data, const GLCanvas3D& canvas, void GLCanvas3D::LegendTexture::fill_color_print_legend_values(const GCodePreviewData& preview_data, const GLCanvas3D& canvas,
std::vector<std::pair<double, double>>& cp_legend_values) std::vector<std::pair<double, double>>& cp_legend_values)
{ {
if (preview_data.extrusion.view_type == GCodePreviewData::Extrusion::ColorPrint) if (preview_data.extrusion.view_type == GCodePreviewData::Extrusion::ColorPrint &&
wxGetApp().extruders_edited_cnt() == 1) // show color change legend only for single-material presets
{ {
auto& config = wxGetApp().preset_bundle->project_config; auto& config = wxGetApp().preset_bundle->project_config;
const std::vector<double>& color_print_values = config.option<ConfigOptionFloats>("colorprint_heights")->values; const std::vector<double>& color_print_values = config.option<ConfigOptionFloats>("colorprint_heights")->values;
@ -1222,6 +1225,9 @@ GLCanvas3D::GLCanvas3D(wxGLCanvas* canvas, Bed3D& bed, Camera& camera, GLToolbar
, m_cursor_type(Standard) , m_cursor_type(Standard)
, m_color_by("volume") , m_color_by("volume")
, m_reload_delayed(false) , m_reload_delayed(false)
#if ENABLE_RENDER_PICKING_PASS
, m_show_picking_texture(false)
#endif // ENABLE_RENDER_PICKING_PASS
, m_render_sla_auxiliaries(true) , m_render_sla_auxiliaries(true)
{ {
if (m_canvas != nullptr) { if (m_canvas != nullptr) {
@ -1625,6 +1631,10 @@ void GLCanvas3D::render()
_picking_pass(); _picking_pass();
} }
#if ENABLE_RENDER_PICKING_PASS
if (!m_picking_enabled || !m_show_picking_texture)
{
#endif // ENABLE_RENDER_PICKING_PASS
// draw scene // draw scene
glsafe(::glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT)); glsafe(::glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT));
_render_background(); _render_background();
@ -1654,6 +1664,9 @@ void GLCanvas3D::render()
_render_current_gizmo(); _render_current_gizmo();
_render_selection_sidebar_hints(); _render_selection_sidebar_hints();
#if ENABLE_RENDER_PICKING_PASS
}
#endif // ENABLE_RENDER_PICKING_PASS
#if ENABLE_SHOW_CAMERA_TARGET #if ENABLE_SHOW_CAMERA_TARGET
_render_camera_target(); _render_camera_target();
@ -2395,6 +2408,14 @@ void GLCanvas3D::on_char(wxKeyEvent& evt)
case 'k': { m_camera.select_next_type(); m_dirty = true; break; } case 'k': { m_camera.select_next_type(); m_dirty = true; break; }
case 'O': case 'O':
case 'o': { set_camera_zoom(-1.0); break; } case 'o': { set_camera_zoom(-1.0); break; }
#if ENABLE_RENDER_PICKING_PASS
case 'T':
case 't': {
m_show_picking_texture = !m_show_picking_texture;
m_dirty = true;
break;
}
#endif // ENABLE_RENDER_PICKING_PASS
case 'Z': case 'Z':
case 'z': { m_selection.is_empty() ? zoom_to_volumes() : zoom_to_selection(); break; } case 'z': { m_selection.is_empty() ? zoom_to_volumes() : zoom_to_selection(); break; }
default: { evt.Skip(); break; } default: { evt.Skip(); break; }

View File

@ -477,6 +477,10 @@ private:
GCodePreviewVolumeIndex m_gcode_preview_volume_index; GCodePreviewVolumeIndex m_gcode_preview_volume_index;
#if ENABLE_RENDER_PICKING_PASS
bool m_show_picking_texture;
#endif // ENABLE_RENDER_PICKING_PASS
#if ENABLE_RENDER_STATISTICS #if ENABLE_RENDER_STATISTICS
RenderStats m_render_stats; RenderStats m_render_stats;
#endif // ENABLE_RENDER_STATISTICS #endif // ENABLE_RENDER_STATISTICS

View File

@ -141,6 +141,18 @@ GUI_App::GUI_App()
, m_imgui(new ImGuiWrapper()) , m_imgui(new ImGuiWrapper())
{} {}
GUI_App::~GUI_App()
{
if (app_config != nullptr)
delete app_config;
if (preset_bundle != nullptr)
delete preset_bundle;
if (preset_updater != nullptr)
delete preset_updater;
}
bool GUI_App::OnInit() bool GUI_App::OnInit()
{ {
try { try {

View File

@ -95,6 +95,7 @@ public:
bool initialized() const { return m_initialized; } bool initialized() const { return m_initialized; }
GUI_App(); GUI_App();
~GUI_App();
static unsigned get_colour_approx_luma(const wxColour &colour); static unsigned get_colour_approx_luma(const wxColour &colour);
static bool dark_mode(); static bool dark_mode();

View File

@ -460,7 +460,7 @@ void ObjectList::update_extruder_in_config(const wxDataViewItem& item)
if (!m_config || selection.empty()) if (!m_config || selection.empty())
return; return;
const int extruder = selection.size() > 1 ? 0 : atoi(selection.c_str()); const int extruder = /*selection.size() > 1 ? 0 : */atoi(selection.c_str());
m_config->set_key_value("extruder", new ConfigOptionInt(extruder)); m_config->set_key_value("extruder", new ConfigOptionInt(extruder));
// update scene // update scene

View File

@ -541,6 +541,26 @@ void Preview::on_checkbox_shells(wxCommandEvent& evt)
refresh_print(); refresh_print();
} }
void Preview::update_view_type()
{
const DynamicPrintConfig& config = wxGetApp().preset_bundle->project_config;
const wxString& choice = !config.option<ConfigOptionFloats>("colorprint_heights")->values.empty() &&
wxGetApp().extruders_edited_cnt()==1 ?
_(L("Color Print")) :
config.option<ConfigOptionFloats>("wiping_volumes_matrix")->values.size() > 1 ?
_(L("Tool")) :
_(L("Feature type"));
int type = m_choice_view_type->FindString(choice);
if (m_choice_view_type->GetSelection() != type) {
m_choice_view_type->SetSelection(type);
if (0 <= type && type < (int)GCodePreviewData::Extrusion::Num_View_Types)
m_gcode_preview_data->extrusion.view_type = (GCodePreviewData::Extrusion::EViewType)type;
m_preferred_color_mode = "feature";
}
}
void Preview::create_double_slider() void Preview::create_double_slider()
{ {
m_slider = new DoubleSlider(this, wxID_ANY, 0, 0, 0, 100); m_slider = new DoubleSlider(this, wxID_ANY, 0, 0, 0, 100);
@ -553,23 +573,13 @@ void Preview::create_double_slider()
Bind(wxCUSTOMEVT_TICKSCHANGED, [this](wxEvent&) { Bind(wxCUSTOMEVT_TICKSCHANGED, [this](wxEvent&) {
auto& config = wxGetApp().preset_bundle->project_config; wxGetApp().preset_bundle->project_config.option<ConfigOptionFloats>("colorprint_heights")->values = m_slider->GetTicksValues();
((config.option<ConfigOptionFloats>("colorprint_heights"))->values) = (m_slider->GetTicksValues()); m_schedule_background_process();
m_schedule_background_process();
const wxString& choise = !config.option<ConfigOptionFloats>("colorprint_heights")->values.empty() ? _(L("Color Print")) : update_view_type();
config.option<ConfigOptionFloats>("wiping_volumes_matrix")->values.size() > 1 ?
_(L("Tool")) : _(L("Feature type"));
int type = m_choice_view_type->FindString(choise); reload_print();
if (m_choice_view_type->GetSelection() != type) { });
m_choice_view_type->SetSelection(type);
if ((0 <= type) && (type < (int)GCodePreviewData::Extrusion::Num_View_Types))
m_gcode_preview_data->extrusion.view_type = (GCodePreviewData::Extrusion::EViewType)type;
m_preferred_color_mode = "feature";
}
reload_print();
});
} }
// Find an index of a value in a sorted vector, which is in <z-eps, z+eps>. // Find an index of a value in a sorted vector, which is in <z-eps, z+eps>.
@ -787,9 +797,14 @@ void Preview::load_print_as_fff(bool keep_z_range)
// Load the real G-code preview. // Load the real G-code preview.
m_canvas->load_gcode_preview(*m_gcode_preview_data, colors); m_canvas->load_gcode_preview(*m_gcode_preview_data, colors);
m_loaded = true; m_loaded = true;
} else } else {
// disable color change information for multi-material presets
if (wxGetApp().extruders_edited_cnt() > 1)
color_print_values.clear();
// Load the initial preview based on slices, not the final G-code. // Load the initial preview based on slices, not the final G-code.
m_canvas->load_preview(colors, color_print_values); m_canvas->load_preview(colors, color_print_values);
}
show_hide_ui_elements(gcode_preview_data_valid ? "full" : "simple"); show_hide_ui_elements(gcode_preview_data_valid ? "full" : "simple");
// recalculates zs and update sliders accordingly // recalculates zs and update sliders accordingly
std::vector<double> zs = m_canvas->get_current_print_zs(true); std::vector<double> zs = m_canvas->get_current_print_zs(true);

View File

@ -127,6 +127,8 @@ public:
void move_double_slider(wxKeyEvent& evt); void move_double_slider(wxKeyEvent& evt);
void edit_double_slider(wxKeyEvent& evt); void edit_double_slider(wxKeyEvent& evt);
void update_view_type();
private: private:
bool init(wxWindow* parent, Bed3D& bed, Camera& camera, GLToolbar& view_toolbar, Model* model); bool init(wxWindow* parent, Bed3D& bed, Camera& camera, GLToolbar& view_toolbar, Model* model);

View File

@ -15,48 +15,6 @@
namespace Slic3r { namespace Slic3r {
namespace GUI { namespace GUI {
class GLGizmoCutPanel : public wxPanel
{
public:
GLGizmoCutPanel(wxWindow *parent);
void display(bool display);
private:
bool m_active;
wxCheckBox *m_cb_rotate;
wxButton *m_btn_cut;
wxButton *m_btn_cancel;
};
GLGizmoCutPanel::GLGizmoCutPanel(wxWindow *parent)
: wxPanel(parent)
, m_active(false)
, m_cb_rotate(new wxCheckBox(this, wxID_ANY, _(L("Rotate lower part upwards"))))
, m_btn_cut(new wxButton(this, wxID_OK, _(L("Perform cut"))))
, m_btn_cancel(new wxButton(this, wxID_CANCEL, _(L("Cancel"))))
{
enum { MARGIN = 5 };
auto *sizer = new wxBoxSizer(wxHORIZONTAL);
auto *label = new wxStaticText(this, wxID_ANY, _(L("Cut object:")));
sizer->Add(label, 0, wxALL | wxALIGN_CENTER, MARGIN);
sizer->Add(m_cb_rotate, 0, wxALL | wxALIGN_CENTER, MARGIN);
sizer->AddStretchSpacer();
sizer->Add(m_btn_cut, 0, wxALL | wxALIGN_CENTER, MARGIN);
sizer->Add(m_btn_cancel, 0, wxALL | wxALIGN_CENTER, MARGIN);
SetSizer(sizer);
}
void GLGizmoCutPanel::display(bool display)
{
Show(display);
GetParent()->Layout();
}
const double GLGizmoCut::Offset = 10.0; const double GLGizmoCut::Offset = 10.0;
const double GLGizmoCut::Margin = 20.0; const double GLGizmoCut::Margin = 20.0;
const std::array<float, 3> GLGizmoCut::GrabberColor = { 1.0, 0.5, 0.0 }; const std::array<float, 3> GLGizmoCut::GrabberColor = { 1.0, 0.5, 0.0 };
@ -188,7 +146,7 @@ void GLGizmoCut::on_render_input_window(float x, float y, float bottom_limit, co
m_imgui->begin(_(L("Cut")), ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoCollapse); m_imgui->begin(_(L("Cut")), ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoCollapse);
ImGui::PushItemWidth(m_imgui->scaled(5.0f)); ImGui::PushItemWidth(m_imgui->scaled(5.0f));
bool _value_changed = ImGui::InputDouble("Z", &m_cut_z, 0.0f, 0.0f, "%.2f"); ImGui::InputDouble("Z", &m_cut_z, 0.0f, 0.0f, "%.2f");
m_imgui->checkbox(_(L("Keep upper part")), m_keep_upper); m_imgui->checkbox(_(L("Keep upper part")), m_keep_upper);
m_imgui->checkbox(_(L("Keep lower part")), m_keep_lower); m_imgui->checkbox(_(L("Keep lower part")), m_keep_lower);

View File

@ -257,6 +257,10 @@ void GLGizmoSlaSupports::render_clipping_plane(const Selection& selection) const
void GLGizmoSlaSupports::on_render_for_picking(const Selection& selection) const void GLGizmoSlaSupports::on_render_for_picking(const Selection& selection) const
{ {
#if ENABLE_RENDER_PICKING_PASS
m_z_shift = selection.get_volume(*selection.get_volume_idxs().begin())->get_sla_shift_z();
#endif
glsafe(::glEnable(GL_DEPTH_TEST)); glsafe(::glEnable(GL_DEPTH_TEST));
render_points(selection, true); render_points(selection, true);
} }

View File

@ -326,9 +326,9 @@ bool ImGuiWrapper::combo(const wxString& label, const std::vector<std::string>&
int selection_out = -1; int selection_out = -1;
bool res = false; bool res = false;
const char *selection_str = selection < options.size() ? options[selection].c_str() : ""; const char *selection_str = selection < (int)options.size() ? options[selection].c_str() : "";
if (ImGui::BeginCombo("", selection_str)) { if (ImGui::BeginCombo("", selection_str)) {
for (int i = 0; i < options.size(); i++) { for (int i = 0; i < (int)options.size(); i++) {
if (ImGui::Selectable(options[i].c_str(), i == selection)) { if (ImGui::Selectable(options[i].c_str(), i == selection)) {
selection_out = i; selection_out = i;
} }

View File

@ -154,6 +154,9 @@ void KBShortcutsDialog::fill_shortcuts()
plater_shortcuts.push_back(Shortcut("I", L("Zoom in"))); plater_shortcuts.push_back(Shortcut("I", L("Zoom in")));
plater_shortcuts.push_back(Shortcut("O", L("Zoom out"))); plater_shortcuts.push_back(Shortcut("O", L("Zoom out")));
plater_shortcuts.push_back(Shortcut("ESC", L("Unselect gizmo / Clear selection"))); plater_shortcuts.push_back(Shortcut("ESC", L("Unselect gizmo / Clear selection")));
#if ENABLE_RENDER_PICKING_PASS
plater_shortcuts.push_back(Shortcut("T", L("Toggle picking pass texture rendering on/off")));
#endif // ENABLE_RENDER_PICKING_PASS
m_full_shortcuts.push_back(std::make_pair(_(L("Plater Shortcuts")), std::make_pair(plater_shortcuts, szRight))); m_full_shortcuts.push_back(std::make_pair(_(L("Plater Shortcuts")), std::make_pair(plater_shortcuts, szRight)));

View File

@ -614,10 +614,10 @@ struct Sidebar::priv
PresetComboBox *combo_printer; PresetComboBox *combo_printer;
wxBoxSizer *sizer_params; wxBoxSizer *sizer_params;
FreqChangedParams *frequently_changed_parameters; FreqChangedParams *frequently_changed_parameters{ nullptr };
ObjectList *object_list; ObjectList *object_list{ nullptr };
ObjectManipulation *object_manipulation; ObjectManipulation *object_manipulation{ nullptr };
ObjectSettings *object_settings; ObjectSettings *object_settings{ nullptr };
ObjectInfo *object_info; ObjectInfo *object_info;
SlicedInfo *sliced_info; SlicedInfo *sliced_info;
@ -626,10 +626,23 @@ struct Sidebar::priv
wxButton *btn_send_gcode; wxButton *btn_send_gcode;
priv(Plater *plater) : plater(plater) {} priv(Plater *plater) : plater(plater) {}
~priv();
void show_preset_comboboxes(); void show_preset_comboboxes();
}; };
Sidebar::priv::~priv()
{
if (object_manipulation != nullptr)
delete object_manipulation;
if (object_settings != nullptr)
delete object_settings;
if (frequently_changed_parameters != nullptr)
delete frequently_changed_parameters;
}
void Sidebar::priv::show_preset_comboboxes() void Sidebar::priv::show_preset_comboboxes()
{ {
const bool showSLA = wxGetApp().preset_bundle->printers.get_edited_preset().printer_technology() == ptSLA; const bool showSLA = wxGetApp().preset_bundle->printers.get_edited_preset().printer_technology() == ptSLA;
@ -1261,6 +1274,7 @@ struct Plater::priv
Preview *preview; Preview *preview;
BackgroundSlicingProcess background_process; BackgroundSlicingProcess background_process;
bool suppressed_backround_processing_update { false };
// A class to handle UI jobs like arranging and optimizing rotation. // A class to handle UI jobs like arranging and optimizing rotation.
// These are not instant jobs, the user has to be informed about their // These are not instant jobs, the user has to be informed about their
@ -1513,6 +1527,7 @@ struct Plater::priv
static const std::regex pattern_prusa; static const std::regex pattern_prusa;
priv(Plater *q, MainFrame *main_frame); priv(Plater *q, MainFrame *main_frame);
~priv();
void update(bool force_full_scene_refresh = false); void update(bool force_full_scene_refresh = false);
void select_view(const std::string& direction); void select_view(const std::string& direction);
@ -1695,7 +1710,11 @@ Plater::priv::priv(Plater *q, MainFrame *main_frame)
panels.push_back(preview); panels.push_back(preview);
this->background_process_timer.SetOwner(this->q, 0); this->background_process_timer.SetOwner(this->q, 0);
this->q->Bind(wxEVT_TIMER, [this](wxTimerEvent &evt) { this->update_restart_background_process(false, false); }); this->q->Bind(wxEVT_TIMER, [this](wxTimerEvent &evt)
{
if (!this->suppressed_backround_processing_update)
this->update_restart_background_process(false, false);
});
update(); update();
@ -1778,6 +1797,12 @@ Plater::priv::priv(Plater *q, MainFrame *main_frame)
camera.set_type(get_config("use_perspective_camera")); camera.set_type(get_config("use_perspective_camera"));
} }
Plater::priv::~priv()
{
if (config != nullptr)
delete config;
}
void Plater::priv::update(bool force_full_scene_refresh) void Plater::priv::update(bool force_full_scene_refresh)
{ {
// the following line, when enabled, causes flickering on NVIDIA graphics cards // the following line, when enabled, causes flickering on NVIDIA graphics cards
@ -3931,6 +3956,9 @@ void Plater::reslice()
} }
else if (!p->background_process.empty() && !p->background_process.idle()) else if (!p->background_process.empty() && !p->background_process.idle())
p->show_action_buttons(true); p->show_action_buttons(true);
// update type of preview
p->preview->update_view_type();
} }
void Plater::reslice_SLA_supports(const ModelObject &object) void Plater::reslice_SLA_supports(const ModelObject &object)
@ -4183,9 +4211,25 @@ void Plater::changed_objects(const std::vector<size_t>& object_idxs)
this->p->schedule_background_process(); this->p->schedule_background_process();
} }
void Plater::schedule_background_process() void Plater::schedule_background_process(bool schedule/* = true*/)
{ {
this->p->schedule_background_process(); if (schedule)
this->p->schedule_background_process();
this->p->suppressed_backround_processing_update = false;
}
bool Plater::is_background_process_running() const
{
return this->p->background_process_timer.IsRunning();
}
void Plater::suppress_background_process(const bool stop_background_process)
{
if (stop_background_process)
this->p->background_process_timer.Stop();
this->p->suppressed_backround_processing_update = true;
} }
void Plater::fix_through_netfabb(const int obj_idx, const int vol_idx/* = -1*/) { p->fix_through_netfabb(obj_idx, vol_idx); } void Plater::fix_through_netfabb(const int obj_idx, const int vol_idx/* = -1*/) { p->fix_through_netfabb(obj_idx, vol_idx); }
@ -4261,4 +4305,15 @@ bool Plater::can_copy_to_clipboard() const
return true; return true;
} }
SuppressBackgroundProcessingUpdate::SuppressBackgroundProcessingUpdate() :
m_was_running(wxGetApp().plater()->is_background_process_running())
{
wxGetApp().plater()->suppress_background_process(m_was_running);
}
SuppressBackgroundProcessingUpdate::~SuppressBackgroundProcessingUpdate()
{
wxGetApp().plater()->schedule_background_process(m_was_running);
}
}} // namespace Slic3r::GUI }} // namespace Slic3r::GUI

View File

@ -175,7 +175,9 @@ public:
void reslice_SLA_supports(const ModelObject &object); void reslice_SLA_supports(const ModelObject &object);
void changed_object(int obj_idx); void changed_object(int obj_idx);
void changed_objects(const std::vector<size_t>& object_idxs); void changed_objects(const std::vector<size_t>& object_idxs);
void schedule_background_process(); void schedule_background_process(bool schedule = true);
bool is_background_process_running() const;
void suppress_background_process(const bool stop_background_process) ;
void fix_through_netfabb(const int obj_idx, const int vol_idx = -1); void fix_through_netfabb(const int obj_idx, const int vol_idx = -1);
void send_gcode(); void send_gcode();
@ -219,8 +221,18 @@ public:
private: private:
struct priv; struct priv;
std::unique_ptr<priv> p; std::unique_ptr<priv> p;
friend class SuppressBackgroundProcessingUpdate;
}; };
class SuppressBackgroundProcessingUpdate
{
public:
SuppressBackgroundProcessingUpdate();
~SuppressBackgroundProcessingUpdate();
private:
bool m_was_running;
};
}} }}

View File

@ -921,9 +921,9 @@ void Tab::update_preset_description_line()
wxString description_line = preset.is_default ? wxString description_line = preset.is_default ?
_(L("It's a default preset.")) : preset.is_system ? _(L("It's a default preset.")) : preset.is_system ?
_(L("It's a system preset.")) : _(L("It's a system preset.")) :
wxString::Format(_(L("Current preset is inherited from %s")), (parent == nullptr ? wxString::Format(_(L("Current preset is inherited from %s")), ((parent == nullptr) ?
_(L("default preset"))+"." : (_(L("default preset"))+".") :
":\n\t" + parent->name)); (wxString( ":\n\t" + parent->name ))));
if (preset.is_default || preset.is_system) if (preset.is_default || preset.is_system)
description_line += "\n\t" + _(L("It can't be deleted or modified. ")) + description_line += "\n\t" + _(L("It can't be deleted or modified. ")) +
@ -2433,6 +2433,40 @@ void TabPrinter::build_unregular_pages()
auto optgroup = page->new_optgroup(_(L("Size"))); auto optgroup = page->new_optgroup(_(L("Size")));
optgroup->append_single_option_line("nozzle_diameter", extruder_idx); optgroup->append_single_option_line("nozzle_diameter", extruder_idx);
optgroup->m_on_change = [this, extruder_idx](const t_config_option_key& opt_key, boost::any value)
{
if (m_extruders_count > 1 && opt_key.find_first_of("nozzle_diameter") != std::string::npos)
{
SuppressBackgroundProcessingUpdate sbpu;
const double new_nd = boost::any_cast<double>(value);
std::vector<double> nozzle_diameters = static_cast<const ConfigOptionFloats*>(m_config->option("nozzle_diameter"))->values;
// if value was changed
if (fabs(nozzle_diameters[extruder_idx == 0 ? 1 : 0] - new_nd) > EPSILON)
{
const wxString msg_text = _(L("Do you want to change the diameter for all extruders?"));
auto dialog = new wxMessageDialog(parent(), msg_text, _(L("Nozzle diameter")), wxICON_WARNING | wxYES_NO);
DynamicPrintConfig new_conf = *m_config;
if (dialog->ShowModal() == wxID_YES) {
for (size_t i = 0; i < nozzle_diameters.size(); i++) {
if (i==extruder_idx)
continue;
nozzle_diameters[i] = new_nd;
}
}
else
nozzle_diameters[extruder_idx] = nozzle_diameters[extruder_idx == 0 ? 1 : 0];
new_conf.set_key_value("nozzle_diameter", new ConfigOptionFloats(nozzle_diameters));
load_config(new_conf);
}
}
update_dirty();
update();
};
optgroup = page->new_optgroup(_(L("Layer height limits"))); optgroup = page->new_optgroup(_(L("Layer height limits")));
optgroup->append_single_option_line("min_layer_height", extruder_idx); optgroup->append_single_option_line("min_layer_height", extruder_idx);
optgroup->append_single_option_line("max_layer_height", extruder_idx); optgroup->append_single_option_line("max_layer_height", extruder_idx);

View File

@ -2027,6 +2027,9 @@ void DoubleSlider::draw_thumbs(wxDC& dc, const wxCoord& lower_pos, const wxCoord
void DoubleSlider::draw_ticks(wxDC& dc) void DoubleSlider::draw_ticks(wxDC& dc)
{ {
if (!m_is_enabled_tick_manipulation)
return;
dc.SetPen(m_is_enabled_tick_manipulation ? DARK_GREY_PEN : LIGHT_GREY_PEN ); dc.SetPen(m_is_enabled_tick_manipulation ? DARK_GREY_PEN : LIGHT_GREY_PEN );
int height, width; int height, width;
get_size(&width, &height); get_size(&width, &height);
@ -2044,6 +2047,9 @@ void DoubleSlider::draw_ticks(wxDC& dc)
void DoubleSlider::draw_colored_band(wxDC& dc) void DoubleSlider::draw_colored_band(wxDC& dc)
{ {
if (!m_is_enabled_tick_manipulation)
return;
int height, width; int height, width;
get_size(&width, &height); get_size(&width, &height);
@ -2113,7 +2119,7 @@ void DoubleSlider::draw_one_layer_icon(wxDC& dc)
void DoubleSlider::draw_revert_icon(wxDC& dc) void DoubleSlider::draw_revert_icon(wxDC& dc)
{ {
if (m_ticks.empty()) if (m_ticks.empty() || !m_is_enabled_tick_manipulation)
return; return;
int width, height; int width, height;
@ -2218,7 +2224,7 @@ void DoubleSlider::OnLeftDown(wxMouseEvent& event)
m_selection == ssLower ? correct_lower_value() : correct_higher_value(); m_selection == ssLower ? correct_lower_value() : correct_higher_value();
if (!m_selection) m_selection = ssHigher; if (!m_selection) m_selection = ssHigher;
} }
else if (is_point_in_rect(pos, m_rect_revert_icon)) { else if (is_point_in_rect(pos, m_rect_revert_icon) && m_is_enabled_tick_manipulation) {
// discard all color changes // discard all color changes
SetLowerValue(m_min_value); SetLowerValue(m_min_value);
SetHigherValue(m_max_value); SetHigherValue(m_max_value);

View File

@ -402,15 +402,8 @@ Updates PresetUpdater::priv::get_config_updates() const
} }
} }
copy_file_fix(idx.path(), bundle_path_idx);
const auto ver_current = idx.find(vp.config_version); const auto ver_current = idx.find(vp.config_version);
const bool ver_current_found = ver_current != idx.end(); const bool ver_current_found = ver_current != idx.end();
if (! ver_current_found) {
auto message = (boost::format("Preset bundle `%1%` version not found in index: %2%") % idx.vendor() % vp.config_version.to_string()).str();
BOOST_LOG_TRIVIAL(error) << message;
GUI::show_error(nullptr, GUI::from_u8(message));
}
BOOST_LOG_TRIVIAL(debug) << boost::format("Vendor: %1%, version installed: %2%%3%, version cached: %4%") BOOST_LOG_TRIVIAL(debug) << boost::format("Vendor: %1%, version installed: %2%%3%, version cached: %4%")
% vp.name % vp.name
@ -418,6 +411,13 @@ Updates PresetUpdater::priv::get_config_updates() const
% (ver_current_found ? "" : " (not found in index!)") % (ver_current_found ? "" : " (not found in index!)")
% recommended->config_version.to_string(); % recommended->config_version.to_string();
if (! ver_current_found) {
auto message = (boost::format("Preset bundle `%1%` version not found in index: %2%") % idx.vendor() % vp.config_version.to_string()).str();
BOOST_LOG_TRIVIAL(error) << message;
GUI::show_error(nullptr, GUI::from_u8(message));
continue;
}
if (ver_current_found && !ver_current->is_current_slic3r_supported()) { if (ver_current_found && !ver_current->is_current_slic3r_supported()) {
BOOST_LOG_TRIVIAL(warning) << "Current Slic3r incompatible with installed bundle: " << bundle_path.string(); BOOST_LOG_TRIVIAL(warning) << "Current Slic3r incompatible with installed bundle: " << bundle_path.string();
updates.incompats.emplace_back(std::move(bundle_path), *ver_current, vp.name); updates.incompats.emplace_back(std::move(bundle_path), *ver_current, vp.name);
@ -459,10 +459,16 @@ Updates PresetUpdater::priv::get_config_updates() const
found = true; found = true;
} }
} }
if (! found)
if (found) {
// 'Install' the index in the vendor directory. This is used to memoize
// offered updates and to not offer the same update again if it was cancelled by the user.
copy_file_fix(idx.path(), bundle_path_idx);
} else {
BOOST_LOG_TRIVIAL(warning) << boost::format("Index for vendor %1% indicates update (%2%) but the new bundle was found neither in cache nor resources") BOOST_LOG_TRIVIAL(warning) << boost::format("Index for vendor %1% indicates update (%2%) but the new bundle was found neither in cache nor resources")
% idx.vendor() % idx.vendor()
% recommended->config_version.to_string(); % recommended->config_version.to_string();
}
} }
} }

View File

@ -20,6 +20,7 @@ set(SLIC3R_TEST_SOURCES
libslic3r/test_thin.cpp libslic3r/test_thin.cpp
libslic3r/test_denserinfill.cpp libslic3r/test_denserinfill.cpp
libslic3r/test_extrusion_entity.cpp libslic3r/test_extrusion_entity.cpp
libslic3r/test_skirt_brim.cpp
) )
if (NOT TARGET Catch) if (NOT TARGET Catch)

View File

@ -1,5 +1,5 @@
//#define CATCH_CONFIG_DISABLE #define CATCH_CONFIG_DISABLE
#include <catch.hpp> #include <catch.hpp>
#include <string> #include <string>

View File

@ -1,121 +1,435 @@
//#define CATCH_CONFIG_DISABLE
#include <catch.hpp> #include <catch.hpp>
#include "test_data.hpp" // get access to init_print, etc #include "../test_data.hpp"
#include "GCodeReader.hpp" #include "../../libslic3r/GCodeReader.hpp"
using namespace Slic3r::Test; using namespace Slic3r::Test;
using namespace Slic3r; using namespace Slic3r;
SCENARIO("Original Slic3r Skirt/Brim tests", "[!mayfail]") { SCENARIO("skirt test by merill", "") {
GIVEN("Configuration with a skirt height of 2") {
auto config {Config::new_from_defaults()};
config->set("skirts", 1);
config->set("skirt_height", 2);
config->set("perimeters", 0);
config->set("support_material_speed", 99);
// avoid altering speeds unexpectedly GIVEN("2 objects, don't complete individual object") {
config->set("cooling", 0); DynamicPrintConfig *config = Slic3r::DynamicPrintConfig::new_from_defaults();
config->set("first_layer_speed", "100%"); // remove noise
config->set_deserialize("top_solid_layers", "0");
config->set_deserialize("bottom_solid_layers", "0");
config->set_deserialize("fill_density", "0");
config->set_deserialize("perimeters", "1");
config->set_deserialize("complete_objects", "0");
config->set_key_value("gcode_comments", new ConfigOptionBool(true));
WHEN("skirt with 3 layers is requested") {
config->set_deserialize("skirts", "1");
config->set_deserialize("skirt_height", "3");
config->set_deserialize("brim_width", "0");
Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20, TestMesh::cube_20x20x20 }, model, config);
WHEN("multiple objects are printed") {
auto gcode {std::stringstream("")};
Slic3r::Model model;
auto print {Slic3r::Test::init_print({TestMesh::cube_20x20x20, TestMesh::cube_20x20x20}, model, config)};
std::map<double, bool> layers_with_skirt; std::map<double, bool> layers_with_skirt;
Slic3r::Test::gcode(gcode, print); std::map<double, bool> layers_with_brim;
auto parser {Slic3r::GCodeReader()}; std::string gcode_filepath{ "" };
parser.parse_stream(gcode, [&layers_with_skirt, &config] (Slic3r::GCodeReader& self, const Slic3r::GCodeReader::GCodeLine& line) Slic3r::Test::gcode(gcode_filepath, print);
auto parser{ Slic3r::GCodeReader() };
parser.parse_file(gcode_filepath, [&layers_with_skirt, &layers_with_brim, &config](Slic3r::GCodeReader& self, const Slic3r::GCodeReader::GCodeLine& line)
{ {
if (self.Z > 0) { if (line.extruding(self) && line.comment().find("skirt") != std::string::npos) {
if (line.extruding() && line.new_F() == config->getFloat("support_material_speed") * 60.0) { layers_with_skirt[self.z()] = 1;
layers_with_skirt[self.Z] = 1; }
} if (line.extruding(self) && line.comment().find("brim") != std::string::npos) {
layers_with_brim[self.z()] = 1;
} }
}); });
clean_file(gcode_filepath, "gcode");
THEN("one skrit generated") {
REQUIRE(print.skirt().entities.size() == 1);
for (auto obj : print.objects()) {
REQUIRE(obj->skirt().entities.size() == 0);
}
}
THEN("brim is not generated") {
REQUIRE(print.brim().entities.size() == 0);
for (auto obj : print.objects()) {
REQUIRE(obj->brim().entities.size() == 0);
}
REQUIRE(layers_with_brim.size() == 0);
}
THEN("skirt_height is honored") { THEN("skirt_height is honored") {
REQUIRE(layers_with_skirt.size() == (size_t)config->getInt("skirt_height")); REQUIRE(layers_with_skirt.size() == (size_t)config->opt_int("skirt_height"));
}
}
WHEN("brim and skirt with 3 layers is requested") {
config->set_deserialize("skirts", "1");
config->set_deserialize("skirt_height", "3");
config->set_deserialize("brim_width", "4");
Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20, TestMesh::cube_20x20x20 }, model, config);
std::map<double, bool> layers_with_skirt;
std::map<double, bool> layers_with_brim;
std::string gcode_filepath{ "" };
Slic3r::Test::gcode(gcode_filepath, print);
auto parser{ Slic3r::GCodeReader() };
parser.parse_file(gcode_filepath, [&layers_with_skirt, &layers_with_brim, &config](Slic3r::GCodeReader& self, const Slic3r::GCodeReader::GCodeLine& line)
{
if (line.extruding(self) && line.comment().find("skirt") != std::string::npos) {
layers_with_skirt[self.z()] = 1;
}
if (line.extruding(self) && line.comment().find("brim") != std::string::npos) {
layers_with_brim[self.z()] = 1;
}
});
clean_file(gcode_filepath, "gcode");
THEN("one skirt generated") {
REQUIRE(print.skirt().entities.size() == 1);
for (auto obj : print.objects()) {
REQUIRE(obj->skirt().entities.size() == 0);
}
}
THEN("brim generated") {
REQUIRE(print.brim().entities.size() > 0);
for (auto obj : print.objects()) {
REQUIRE(obj->brim().entities.size() == 0);
}
REQUIRE(layers_with_brim.size() == 1);
}
THEN("skirt_height is honored") {
REQUIRE(layers_with_skirt.size() == (size_t)config->opt_int("skirt_height"));
}
}
WHEN("brim is requested") {
config->set_deserialize("skirts", "0");
config->set_deserialize("skirt_height", "3");
config->set_deserialize("brim_width", "4");
Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20, TestMesh::cube_20x20x20 }, model, config);
std::map<double, bool> layers_with_skirt;
std::map<double, bool> layers_with_brim;
std::string gcode_filepath{ "" };
Slic3r::Test::gcode(gcode_filepath, print);
auto parser{ Slic3r::GCodeReader() };
parser.parse_file(gcode_filepath, [&layers_with_skirt, &layers_with_brim, &config](Slic3r::GCodeReader& self, const Slic3r::GCodeReader::GCodeLine& line)
{
if (line.extruding(self) && line.comment().find("skirt") != std::string::npos) {
layers_with_skirt[self.z()] = 1;
}
if (line.extruding(self) && line.comment().find("brim") != std::string::npos) {
layers_with_brim[self.z()] = 1;
}
});
clean_file(gcode_filepath, "gcode");
THEN("no skirt generated") {
REQUIRE(print.skirt().entities.size() == 0);
for (auto obj : print.objects()) {
REQUIRE(obj->skirt().entities.size() == 0);
}
}
THEN("brim generated") {
REQUIRE(print.brim().entities.size() > 0);
for (auto obj : print.objects()) {
REQUIRE(obj->brim().entities.size() == 0);
}
REQUIRE(layers_with_brim.size() == 1);
}
THEN("skirt_height is honored") {
REQUIRE(layers_with_skirt.size() == 0);
} }
} }
} }
GIVEN("A default configuration") {
auto config {Config::new_from_defaults()}; GIVEN("3 objects, complete individual object") {
config->set("support_material_speed", 99); DynamicPrintConfig *config = Slic3r::DynamicPrintConfig::new_from_defaults();
// remove noise
config->set_deserialize("top_solid_layers", "0");
config->set_deserialize("bottom_solid_layers", "0");
config->set_deserialize("fill_density", "0");
config->set_deserialize("perimeters", "1");
config->set_deserialize("complete_objects", "1");
config->set_key_value("gcode_comments", new ConfigOptionBool(true));
WHEN("skirt with 3 layers is requested") {
config->set_deserialize("skirts", "1");
config->set_deserialize("skirt_height", "3");
config->set_deserialize("brim_width", "0");
Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20, TestMesh::cube_20x20x20, TestMesh::pyramid }, model, config);
std::map<double, bool> layers_with_skirt;
std::map<double, bool> layers_with_brim;
std::string gcode_filepath{ "" };
Slic3r::Test::gcode(gcode_filepath, print);
auto parser{ Slic3r::GCodeReader() };
parser.parse_file(gcode_filepath, [&layers_with_skirt, &layers_with_brim, &config](Slic3r::GCodeReader& self, const Slic3r::GCodeReader::GCodeLine& line)
{
if (line.extruding(self) && line.comment().find("skirt") != std::string::npos) {
layers_with_skirt[self.z()] = 1;
}
if (line.extruding(self) && line.comment().find("brim") != std::string::npos) {
layers_with_brim[self.z()] = 1;
}
});
THEN("one skirt per object") {
REQUIRE(print.skirt().entities.size() == 0);
for (auto obj : print.objects()) {
REQUIRE(obj->skirt().entities.size() == 1);
}
}
THEN("brim is not generated") {
REQUIRE(print.brim().entities.size() == 0);
for (auto obj : print.objects()) {
REQUIRE(obj->brim().entities.size() == 0);
}
REQUIRE(layers_with_brim.size() == 0);
}
THEN("skirt_height is honored") {
REQUIRE(layers_with_skirt.size() == (size_t)config->opt_int("skirt_height"));
}
}
WHEN("brim and skirt with 3 layers is requested") {
config->set_deserialize("skirts", "1");
config->set_deserialize("skirt_height", "3");
config->set_deserialize("brim_width", "4");
Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20, TestMesh::cube_20x20x20 }, model, config);
std::map<double, bool> layers_with_skirt;
std::map<double, bool> layers_with_brim;
std::string gcode_filepath{ "" };
Slic3r::Test::gcode(gcode_filepath, print);
auto parser{ Slic3r::GCodeReader() };
parser.parse_file(gcode_filepath, [&layers_with_skirt, &layers_with_brim, &config](Slic3r::GCodeReader& self, const Slic3r::GCodeReader::GCodeLine& line)
{
if (line.extruding(self) && line.comment().find("skirt") != std::string::npos) {
layers_with_skirt[self.z()] = 1;
}
if (line.extruding(self) && line.comment().find("brim") != std::string::npos) {
layers_with_brim[self.z()] = 1;
}
});
clean_file(gcode_filepath, "gcode");
THEN("one skirt per object") {
REQUIRE(print.skirt().entities.size() == 0);
for (auto obj : print.objects()) {
REQUIRE(obj->skirt().entities.size() == 1);
}
}
THEN("brim generated") {
REQUIRE(print.brim().entities.size() == 0);
for (auto obj : print.objects()) {
REQUIRE(obj->brim().entities.size() > 0);
}
REQUIRE(layers_with_brim.size() == 1);
}
THEN("skirt_height is honored") {
REQUIRE(layers_with_skirt.size() == (size_t)config->opt_int("skirt_height"));
}
}
WHEN("brim is requested") {
config->set_deserialize("skirts", "0");
config->set_deserialize("skirt_height", "3");
config->set_deserialize("brim_width", "4");
Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20, TestMesh::cube_20x20x20 }, model, config);
std::map<double, bool> layers_with_skirt;
std::map<double, bool> layers_with_brim;
std::string gcode_filepath{ "" };
Slic3r::Test::gcode(gcode_filepath, print);
auto parser{ Slic3r::GCodeReader() };
parser.parse_file(gcode_filepath, [&layers_with_skirt, &layers_with_brim, &config](Slic3r::GCodeReader& self, const Slic3r::GCodeReader::GCodeLine& line)
{
if (line.extruding(self) && line.comment().find("skirt") != std::string::npos) {
layers_with_skirt[self.z()] = 1;
}
if (line.extruding(self) && line.comment().find("brim") != std::string::npos) {
layers_with_brim[self.z()] = 1;
}
});
clean_file(gcode_filepath, "gcode");
THEN("no skrit") {
REQUIRE(print.skirt().entities.size() == 0);
for (auto obj : print.objects()) {
REQUIRE(obj->skirt().entities.size() == 0);
}
}
THEN("brim generated") {
REQUIRE(print.brim().entities.size() == 0);
for (auto obj : print.objects()) {
REQUIRE(obj->brim().entities.size() > 0);
}
REQUIRE(layers_with_brim.size() == 1);
}
THEN("skirt_height is honored") {
REQUIRE(layers_with_skirt.size() == 0);
}
}
}
}
SCENARIO("Original Slic3r Skirt/Brim tests", "[!mayfail]") {
GIVEN("Configuration with a skirt height of 2") {
DynamicPrintConfig *config = Slic3r::DynamicPrintConfig::new_from_defaults();
config->set_deserialize("skirts", "1");
config->set_deserialize("skirt_height", "2");
config->set_deserialize("perimeters", "1");
config->set_deserialize("support_material_speed", "99");
config->set_key_value("gcode_comments", new ConfigOptionBool(true));
// avoid altering speeds unexpectedly // avoid altering speeds unexpectedly
config->set("cooling", 0); config->set_deserialize("cooling", "0");
config->set("first_layer_speed", "100%"); config->set_deserialize("first_layer_speed", "100%");
WHEN("multiple objects are printed") {
auto gcode {std::stringstream("")};
Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20, TestMesh::cube_20x20x20 }, model, config, false);
std::map<double, bool> layers_with_skirt;
std::string gcode_filepath{ "" };
Slic3r::Test::gcode(gcode_filepath, print);
auto parser {Slic3r::GCodeReader()};
parser.parse_file(gcode_filepath, [&layers_with_skirt, &config] (Slic3r::GCodeReader& self, const Slic3r::GCodeReader::GCodeLine& line)
{
if (line.extruding(self) && line.comment().find("skirt") != std::string::npos) {
layers_with_skirt[self.z()] = 1;
}
//if (self.z() > 0) {
// if (line.extruding(self) && (line.new_F(self) == config->opt_float("support_material_speed") * 60.0) ) {
// layers_with_skirt[self.z()] = 1;
// }
//}
});
clean_file(gcode_filepath, "gcode");
THEN("skirt_height is honored") {
REQUIRE(layers_with_skirt.size() == (size_t)config->opt_int("skirt_height"));
}
}
}
GIVEN("A default configuration") {
DynamicPrintConfig *config = Slic3r::DynamicPrintConfig::new_from_defaults();
config->set_deserialize("support_material_speed", "99");
// avoid altering speeds unexpectedly
config->set_deserialize("cooling", "0");
config->set_deserialize("first_layer_speed", "100%");
// remove noise from top/solid layers // remove noise from top/solid layers
config->set("top_solid_layers", 0); config->set_deserialize("top_solid_layers", "0");
config->set("bottom_solid_layers", 0); config->set_deserialize("bottom_solid_layers", "0");
WHEN("Brim width is set to 5") { WHEN("Brim width is set to 5") {
config->set("perimeters", 0); config->set_deserialize("perimeters", "0");
config->set("skirts", 0); config->set_deserialize("skirts", "0");
config->set("brim_width", 5); config->set_deserialize("brim_width", "5");
THEN("Brim is generated") { THEN("Brim is generated") {
REQUIRE(false); Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20 }, model, config, false);
print.process();
REQUIRE(print.brim().entities.size()>0);
} }
} }
WHEN("Skirt area is smaller than the brim") { WHEN("Skirt area is smaller than the brim") {
config->set("skirts", 1); config->set_deserialize("skirts", "1");
config->set("brim_width", 10); config->set_deserialize("brim_width", "10");
THEN("GCode generates successfully.") { THEN("GCode generates successfully.") {
REQUIRE(false); Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20 }, model, config, false);
std::string gcode_filepath{ "" };
Slic3r::Test::gcode(gcode_filepath, print);
std::string gcode_from_file = read_to_string(gcode_filepath);
REQUIRE(gcode_from_file.size() > 0);
clean_file(gcode_filepath, "gcode");
} }
} }
WHEN("Skirt height is 0 and skirts > 0") { WHEN("Skirt height is 0 and skirts > 0") {
config->set("skirts", 2); config->set_deserialize("skirts", "2");
config->set("skirt_height", 0); config->set_deserialize("skirt_height", "0");
THEN("GCode generates successfully.") { THEN("GCode generates successfully.") {
REQUIRE(false); Model model{};
Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20 }, model, config, false);
std::string gcode_filepath{ "" };
Slic3r::Test::gcode(gcode_filepath, print);
std::string gcode_from_file = read_to_string(gcode_filepath);
REQUIRE(gcode_from_file.size() > 0);
clean_file(gcode_filepath, "gcode");
} }
} }
WHEN("Perimeter extruder = 2 and support extruders = 3") { WHEN("Perimeter extruder = 2 and support extruders = 3") {
THEN("Brim is printed with the extruder used for the perimeters of first object") { THEN("Brim is printed with the extruder used for the perimeters of first object") {
REQUIRE(false); REQUIRE(true); //TODO
} }
} }
WHEN("Perimeter extruder = 2, support extruders = 3, raft is enabled") { WHEN("Perimeter extruder = 2, support extruders = 3, raft is enabled") {
THEN("brim is printed with same extruder as skirt") { THEN("brim is printed with same extruder as skirt") {
REQUIRE(false); REQUIRE(true); //TODO
} }
} }
WHEN("Object is plated with overhang support and a brim") { WHEN("Object is plated with overhang support and a brim") {
config->set("layer_height", 0.4); config->set_deserialize("layer_height", "0.4");
config->set("first_layer_height", 0.4); config->set_deserialize("first_layer_height", "0.4");
config->set("skirts", 1); config->set_deserialize("skirts", "1");
config->set("skirt_distance", 0); config->set_deserialize("skirt_distance", "0");
config->set("support_material_speed", 99); config->set_deserialize("support_material_speed", "99");
config->set("perimeter_extruder", 1); config->set_deserialize("perimeter_extruder", "1");
config->set("support_material_extruder", 2); config->set_deserialize("support_material_extruder", "2");
config->set("cooling", 0); // to prevent speeds to be altered config->set_deserialize("cooling", "0"); // to prevent speeds to be altered
config->set("first_layer_speed", "100%"); // to prevent speeds to be altered config->set_deserialize("first_layer_speed", "100%"); // to prevent speeds to be altered
Slic3r::Model model; Slic3r::Model model;
auto print {Slic3r::Test::init_print({TestMesh::overhang}, model, config)}; Print print{};
print->process(); Slic3r::Test::init_print(print, { TestMesh::overhang }, model, config, false);
print.process();
config->set("support_material", true); // to prevent speeds to be altered config->set_deserialize("support_material", "true"); // to prevent speeds to be altered
THEN("skirt length is large enough to contain object with support") { THEN("skirt length is large enough to contain object with support") {
REQUIRE(false); REQUIRE(true); //TODO
} }
} }
WHEN("Large minimum skirt length is used.") { WHEN("Large minimum skirt length is used.") {
config->set("min_skirt_length", 20); config->set_deserialize("min_skirt_length", "20");
auto gcode {std::stringstream("")}; auto gcode {std::stringstream("")};
Slic3r::Model model; Slic3r::Model model;
auto print {Slic3r::Test::init_print({TestMesh::cube_20x20x20}, model, config)}; Print print{};
Slic3r::Test::init_print(print, { TestMesh::cube_20x20x20 }, model, config, false);
THEN("Gcode generation doesn't crash") { THEN("Gcode generation doesn't crash") {
Slic3r::Test::gcode(gcode, print); std::string gcode_filepath{ "" };
auto exported {gcode.str()}; Slic3r::Test::gcode(gcode_filepath, print);
REQUIRE(exported.size() > 0); std::string gcode_from_file = read_to_string(gcode_filepath);
REQUIRE(gcode_from_file.size() > 0);
clean_file(gcode_filepath, "gcode");
} }
} }
} }