From aea5db2933366fa4c9efd16dcd4d806526ee7ac3 Mon Sep 17 00:00:00 2001 From: Scott Lahteine Date: Fri, 31 Mar 2023 15:21:16 -0500 Subject: [PATCH] Cache file count in CardReader --- Marlin/src/feature/easythreed_ui.cpp | 17 ++--- Marlin/src/lcd/e3v2/creality/dwin.cpp | 10 +-- Marlin/src/lcd/e3v2/jyersui/dwin.cpp | 10 +-- Marlin/src/lcd/e3v2/proui/dwin.cpp | 8 +- Marlin/src/lcd/extui/malyan/malyan.cpp | 4 +- .../src/lcd/extui/mks_ui/draw_print_file.cpp | 6 +- Marlin/src/lcd/extui/mks_ui/wifi_module.cpp | 6 +- Marlin/src/lcd/extui/ui_api.cpp | 18 ++--- Marlin/src/lcd/extui/ui_api.h | 3 - Marlin/src/lcd/menu/menu_media.cpp | 10 +-- Marlin/src/sd/cardreader.cpp | 74 ++++++++----------- Marlin/src/sd/cardreader.h | 27 +++---- 12 files changed, 80 insertions(+), 113 deletions(-) diff --git a/Marlin/src/feature/easythreed_ui.cpp b/Marlin/src/feature/easythreed_ui.cpp index b15daffc09bee..39248bfc7d78a 100644 --- a/Marlin/src/feature/easythreed_ui.cpp +++ b/Marlin/src/feature/easythreed_ui.cpp @@ -190,31 +190,28 @@ void EasythreedUI::printButton() { print_key_flag = PF_PAUSE; // The "Print" button now pauses the print card.mount(); // Force SD card to mount - now! if (!card.isMounted) { // Failed to mount? - blink_interval_ms = LED_OFF; // Turn off LED - print_key_flag = PF_START; - return; // Bail out + blink_interval_ms = LED_OFF; // Turn off LED + print_key_flag = PF_START; + return; // Bail out } card.ls(); // List all files to serial output - const uint16_t filecnt = card.countFilesInWorkDir(); // Count printable files in cwd + const int16_t filecnt = card.get_num_items(); // Count printable files in cwd if (filecnt == 0) return; // None are printable? card.selectFileByIndex(filecnt); // Select the last file according to current sort options card.openAndPrintFile(card.filename); // Start printing it - break; - } + } break; case PF_PAUSE: { // Pause printing (not currently firing) if (!printingIsActive()) break; blink_interval_ms = LED_ON; // Set indicator to steady ON queue.inject(F("M25")); // Queue Pause print_key_flag = PF_RESUME; // The "Print" button now resumes the print - break; - } + } break; case PF_RESUME: { // Resume printing if (printingIsActive()) break; blink_interval_ms = LED_BLINK_2; // Blink the indicator LED at 1 second intervals queue.inject(F("M24")); // Queue resume print_key_flag = PF_PAUSE; // The "Print" button now pauses the print - break; - } + } break; } } else { // Register a longer press diff --git a/Marlin/src/lcd/e3v2/creality/dwin.cpp b/Marlin/src/lcd/e3v2/creality/dwin.cpp index 08d928684a6f3..459b00ae1b1e3 100644 --- a/Marlin/src/lcd/e3v2/creality/dwin.cpp +++ b/Marlin/src/lcd/e3v2/creality/dwin.cpp @@ -411,7 +411,7 @@ void Scroll_Menu(const uint8_t dir) { } inline uint16_t nr_sd_menu_items() { - return card.get_num_Files() + !card.flag.workDirIsRoot; + return card.get_num_items() + !card.flag.workDirIsRoot; } void Erase_Menu_Text(const uint8_t line) { @@ -1830,9 +1830,9 @@ void MarlinUI::refresh() { /* Nothing to see here */ } void Init_Shift_Name() { const bool is_subdir = !card.flag.workDirIsRoot; const int8_t filenum = select_file.now - 1 - is_subdir; // Skip "Back" and ".." - const uint16_t fileCnt = card.get_num_Files(); + const int16_t fileCnt = card.get_num_items(); if (WITHIN(filenum, 0, fileCnt - 1)) { - card.getfilename_sorted(SD_ORDER(filenum, fileCnt)); + card.selectFileByIndexSorted(filenum); char * const name = card.longest_filename(); make_name_without_ext(shift_name, name, 100); } @@ -1857,7 +1857,7 @@ void Draw_SDItem(const uint16_t item, int16_t row=-1) { return; } - card.getfilename_sorted(SD_ORDER(item - is_subdir, card.get_num_Files())); + card.selectFileByIndexSorted(item - is_subdir); char * const name = card.longest_filename(); #if ENABLED(SCROLL_LONG_FILENAMES) @@ -2223,7 +2223,7 @@ void HMI_SelectFile() { } else { const uint16_t filenum = select_file.now - 1 - hasUpDir; - card.getfilename_sorted(SD_ORDER(filenum, card.get_num_Files())); + card.selectFileByIndexSorted(filenum); // Enter that folder! if (card.flag.filenameIsDir) { diff --git a/Marlin/src/lcd/e3v2/jyersui/dwin.cpp b/Marlin/src/lcd/e3v2/jyersui/dwin.cpp index 3f13fe8b3bdcd..556aca5fdc80b 100644 --- a/Marlin/src/lcd/e3v2/jyersui/dwin.cpp +++ b/Marlin/src/lcd/e3v2/jyersui/dwin.cpp @@ -808,7 +808,7 @@ void CrealityDWINClass::Draw_SD_Item(uint8_t item, uint8_t row) { if (item == 0) Draw_Menu_Item(0, ICON_Back, card.flag.workDirIsRoot ? F("Back") : F("..")); else { - card.getfilename_sorted(SD_ORDER(item - 1, card.get_num_Files())); + card.selectFileByIndexSorted(item - 1); char * const filename = card.longest_filename(); size_t max = MENU_CHAR_LIMIT; size_t pos = strlen(filename), len = pos; @@ -832,7 +832,7 @@ void CrealityDWINClass::Draw_SD_List(bool removed/*=false*/) { scrollpos = 0; process = File; if (card.isMounted() && !removed) { - LOOP_L_N(i, _MIN(card.get_num_Files() + 1, TROWS)) + LOOP_L_N(i, _MIN(card.get_num_items() + 1, TROWS)) Draw_SD_Item(i, i); } else { @@ -4282,7 +4282,7 @@ void CrealityDWINClass::File_Control() { EncoderState encoder_diffState = Encoder_ReceiveAnalyze(); if (encoder_diffState == ENCODER_DIFF_NO) { if (selection > 0) { - card.getfilename_sorted(SD_ORDER(selection - 1, card.get_num_Files())); + card.selectFileByIndexSorted(selection - 1); char * const filename = card.longest_filename(); size_t len = strlen(filename); size_t pos = len; @@ -4301,7 +4301,7 @@ void CrealityDWINClass::File_Control() { } return; } - if (encoder_diffState == ENCODER_DIFF_CW && selection < card.get_num_Files()) { + if (encoder_diffState == ENCODER_DIFF_CW && selection < card.get_num_items()) { DWIN_Draw_Rectangle(1, Color_Bg_Black, 0, MBASE(selection - scrollpos) - 18, 14, MBASE(selection - scrollpos) + 33); if (selection > 0) { DWIN_Draw_Rectangle(1, Color_Bg_Black, LBLX, MBASE(selection - scrollpos) - 14, 271, MBASE(selection - scrollpos) + 28); @@ -4341,7 +4341,7 @@ void CrealityDWINClass::File_Control() { } } else { - card.getfilename_sorted(SD_ORDER(selection - 1, card.get_num_Files())); + card.selectFileByIndexSorted(selection - 1); if (card.flag.filenameIsDir) { card.cd(card.filename); Draw_SD_List(); diff --git a/Marlin/src/lcd/e3v2/proui/dwin.cpp b/Marlin/src/lcd/e3v2/proui/dwin.cpp index b0d1fb3ff6e1e..adc6fca72aa6a 100644 --- a/Marlin/src/lcd/e3v2/proui/dwin.cpp +++ b/Marlin/src/lcd/e3v2/proui/dwin.cpp @@ -844,7 +844,7 @@ void SetMediaAutoMount() { } inline uint16_t nr_sd_menu_items() { - return _MIN(card.get_num_Files() + !card.flag.workDirIsRoot, MENU_MAX_ITEMS); + return _MIN(card.get_num_items() + !card.flag.workDirIsRoot, MENU_MAX_ITEMS); } void make_name_without_ext(char *dst, char *src, size_t maxlen=MENU_CHAR_LIMIT) { @@ -891,7 +891,7 @@ void onClickSDItem() { if (hasUpDir && CurrentMenu->selected == 1) return SDCard_Up(); else { const uint16_t filenum = CurrentMenu->selected - 1 - hasUpDir; - card.getfilename_sorted(SD_ORDER(filenum, card.get_num_Files())); + card.selectFileByIndexSorted(filenum); // Enter that folder! if (card.flag.filenameIsDir) return SDCard_Folder(card.filename); @@ -934,7 +934,7 @@ void onClickSDItem() { last_itemselected = selected; if (selected >= 1 + hasUpDir) { const int8_t filenum = selected - 1 - hasUpDir; // Skip "Back" and ".." - card.getfilename_sorted(SD_ORDER(filenum, card.get_num_Files())); + card.selectFileByIndexSorted(filenum); make_name_without_ext(shift_name, card.longest_filename(), LONG_FILENAME_LENGTH); shift_len = strlen(shift_name); shift_amt = 0; @@ -959,7 +959,7 @@ void onDrawFileName(MenuItemClass* menuitem, int8_t line) { } else { uint8_t icon; - card.getfilename_sorted(SD_ORDER(menuitem->pos - is_subdir - 1, card.get_num_Files())); + card.selectFileByIndexSorted(menuitem->pos - is_subdir - 1); make_name_without_ext(shift_name, card.longest_filename()); icon = card.flag.filenameIsDir ? ICON_Folder : card.fileIsBinary() ? ICON_Binary : ICON_File; Draw_Menu_Line(line, icon, shift_name); diff --git a/Marlin/src/lcd/extui/malyan/malyan.cpp b/Marlin/src/lcd/extui/malyan/malyan.cpp index 06c9886f01312..66c52878cc981 100644 --- a/Marlin/src/lcd/extui/malyan/malyan.cpp +++ b/Marlin/src/lcd/extui/malyan/malyan.cpp @@ -326,8 +326,8 @@ void process_lcd_s_command(const char *command) { // select a file for printing during a print, there's // little reason not to do it this way. char message_buffer[MAX_CURLY_COMMAND]; - uint16_t file_count = card.get_num_Files(); - for (uint16_t i = 0; i < file_count; i++) { + int16_t file_count = card.get_num_items(); + for (int16_t i = 0; i < file_count; i++) { card.selectFileByIndex(i); sprintf_P(message_buffer, card.flag.filenameIsDir ? PSTR("{DIR:%s}") : PSTR("{FILE:%s}"), card.longest_filename()); write_to_lcd(message_buffer); diff --git a/Marlin/src/lcd/extui/mks_ui/draw_print_file.cpp b/Marlin/src/lcd/extui/mks_ui/draw_print_file.cpp index 0199bc1f555d5..6b41981fb8571 100644 --- a/Marlin/src/lcd/extui/mks_ui/draw_print_file.cpp +++ b/Marlin/src/lcd/extui/mks_ui/draw_print_file.cpp @@ -72,11 +72,11 @@ uint8_t sel_id = 0; else card.cdroot(); - const uint16_t fileCnt = card.get_num_Files(); + const int16_t fileCnt = card.get_num_items(); - for (uint16_t i = 0; i < fileCnt; i++) { + for (int16_t i = 0; i < fileCnt; i++) { if (list_file.Sd_file_cnt == list_file.Sd_file_offset) { - card.getfilename_sorted(SD_ORDER(i, fileCnt)); + card.selectFileByIndexSorted(i); list_file.IsFolder[valid_name_cnt] = card.flag.filenameIsDir; strcpy(list_file.file_name[valid_name_cnt], list_file.curDirPath); diff --git a/Marlin/src/lcd/extui/mks_ui/wifi_module.cpp b/Marlin/src/lcd/extui/mks_ui/wifi_module.cpp index b389109975830..d6d2ce3945dcc 100644 --- a/Marlin/src/lcd/extui/mks_ui/wifi_module.cpp +++ b/Marlin/src/lcd/extui/mks_ui/wifi_module.cpp @@ -823,12 +823,12 @@ uint8_t Explore_Disk(const char * const path, const uint8_t recu_level, const bo if (!path) return 0; - const uint8_t fileCnt = card.get_num_Files(); + const int16_t fileCnt = card.get_num_items(); MediaFile file; MediaFile *diveDir; - for (uint8_t i = 0; i < fileCnt; i++) { - card.getfilename_sorted(SD_ORDER(i, fileCnt)); + for (int16_t i = 0; i < fileCnt; i++) { + card.selectFileByIndexSorted(i); ZERO(Fstream); strcpy(Fstream, card.filename); diff --git a/Marlin/src/lcd/extui/ui_api.cpp b/Marlin/src/lcd/extui/ui_api.cpp index 5c27b345c4476..7e47bef9c147d 100644 --- a/Marlin/src/lcd/extui/ui_api.cpp +++ b/Marlin/src/lcd/extui/ui_api.cpp @@ -1136,12 +1136,12 @@ namespace ExtUI { FileList::FileList() { refresh(); } - void FileList::refresh() { num_files = 0xFFFF; } + void FileList::refresh() { } bool FileList::seek(const uint16_t pos, const bool skip_range_check) { #if ENABLED(SDSUPPORT) if (!skip_range_check && (pos + 1) > count()) return false; - card.getfilename_sorted(SD_ORDER(pos, count())); + card.selectFileByIndexSorted(pos); return card.filename[0] != '\0'; #else UNUSED(pos); @@ -1167,7 +1167,7 @@ namespace ExtUI { } uint16_t FileList::count() { - return TERN0(SDSUPPORT, (num_files = (num_files == 0xFFFF ? card.get_num_Files() : num_files))); + return TERN0(SDSUPPORT, card.get_num_items()); } bool FileList::isAtRootDir() { @@ -1175,19 +1175,11 @@ namespace ExtUI { } void FileList::upDir() { - #if ENABLED(SDSUPPORT) - card.cdup(); - num_files = 0xFFFF; - #endif + TERN_(SDSUPPORT, card.cdup()); } void FileList::changeDir(const char * const dirname) { - #if ENABLED(SDSUPPORT) - card.cd(dirname); - num_files = 0xFFFF; - #else - UNUSED(dirname); - #endif + TERN(SDSUPPORT, card.cd(dirname), UNUSED(dirname)); } } // namespace ExtUI diff --git a/Marlin/src/lcd/extui/ui_api.h b/Marlin/src/lcd/extui/ui_api.h index d9594bace6403..209635ea0944e 100644 --- a/Marlin/src/lcd/extui/ui_api.h +++ b/Marlin/src/lcd/extui/ui_api.h @@ -376,9 +376,6 @@ namespace ExtUI { void resumePrint(); class FileList { - private: - uint16_t num_files; - public: FileList(); void refresh(); diff --git a/Marlin/src/lcd/menu/menu_media.cpp b/Marlin/src/lcd/menu/menu_media.cpp index 20ef6e3d198f9..d43053da6256c 100644 --- a/Marlin/src/lcd/menu/menu_media.cpp +++ b/Marlin/src/lcd/menu/menu_media.cpp @@ -109,10 +109,10 @@ void menu_media_filelist() { ui.encoder_direction_menus(); #if HAS_MARLINUI_U8GLIB - static uint16_t fileCnt; - if (ui.first_page) fileCnt = card.get_num_Files(); + static int16_t fileCnt; + if (ui.first_page) fileCnt = card.get_num_items(); #else - const uint16_t fileCnt = card.get_num_Files(); + const int16_t fileCnt = card.get_num_items(); #endif START_MENU(); @@ -129,9 +129,9 @@ void menu_media_filelist() { else if (card.isMounted()) ACTION_ITEM_F(F(LCD_STR_FOLDER " .."), lcd_sd_updir); - if (ui.should_draw()) for (uint16_t i = 0; i < fileCnt; i++) { + if (ui.should_draw()) for (int16_t i = 0; i < fileCnt; i++) { if (_menuLineNr == _thisItemNr) { - card.getfilename_sorted(SD_ORDER(i, fileCnt)); + card.selectFileByIndexSorted(i); if (card.flag.filenameIsDir) MENU_ITEM(sdfolder, MSG_MEDIA_MENU, card); else diff --git a/Marlin/src/sd/cardreader.cpp b/Marlin/src/sd/cardreader.cpp index 8a4fa743d49dd..038f94c36a044 100644 --- a/Marlin/src/sd/cardreader.cpp +++ b/Marlin/src/sd/cardreader.cpp @@ -81,10 +81,11 @@ IF_DISABLED(NO_SD_AUTOSTART, uint8_t CardReader::autofile_index); // = 0 MediaFile CardReader::root, CardReader::workDir, CardReader::workDirParents[MAX_DIR_DEPTH]; uint8_t CardReader::workDirDepth; +int16_t CardReader::nrFiles = -1; #if ENABLED(SDCARD_SORT_ALPHA) - uint16_t CardReader::sort_count; + int16_t CardReader::sort_count; #if ENABLED(SDSORT_GCODE) bool CardReader::sort_alpha; int CardReader::sort_folders; @@ -100,7 +101,6 @@ uint8_t CardReader::workDirDepth; #if ENABLED(SDSORT_USES_RAM) #if ENABLED(SDSORT_CACHE_NAMES) - uint16_t CardReader::nrFiles; // Cached total file count #if ENABLED(SDSORT_DYNAMIC_RAM) char **CardReader::sortshort, **CardReader::sortnames; #else @@ -228,25 +228,19 @@ bool CardReader::is_visible_entity(const dir_t &p OPTARG(CUSTOM_FIRMWARE_UPLOAD, // // Get the number of (compliant) items in the folder // -int CardReader::countItems(MediaFile dir) { +int16_t CardReader::countItems(MediaFile dir) { dir_t p; - int c = 0; - while (dir.readDir(&p, longFilename) > 0) - c += is_visible_entity(p); - - #if ALL(SDCARD_SORT_ALPHA, SDSORT_USES_RAM, SDSORT_CACHE_NAMES) - nrFiles = c; - #endif - + int16_t c = 0; + while (dir.readDir(&p, longFilename) > 0) c += is_visible_entity(p); return c; } // // Get file/folder info for an item by index // -void CardReader::selectByIndex(MediaFile dir, const uint8_t index) { +void CardReader::selectByIndex(MediaFile dir, const int16_t index) { dir_t p; - for (uint8_t cnt = 0; dir.readDir(&p, longFilename) > 0;) { + for (int16_t cnt = 0; dir.readDir(&p, longFilename) > 0;) { if (is_visible_entity(p)) { if (cnt == index) { createFilename(filename, p); @@ -480,6 +474,7 @@ void CardReader::printSelectedFilename() { void CardReader::mount() { flag.mounted = false; + nrFiles = -1; if (root.isOpen()) root.close(); if (!driver->init(SD_SPI_SPEED, SDSS) @@ -578,9 +573,7 @@ void CardReader::release() { flag.mounted = false; flag.workDirIsRoot = true; - #if ALL(SDCARD_SORT_ALPHA, SDSORT_USES_RAM, SDSORT_CACHE_NAMES) - nrFiles = 0; - #endif + nrFiles = -1; SERIAL_ECHO_MSG(STR_SD_CARD_RELEASED); } @@ -909,7 +902,7 @@ void CardReader::closefile(const bool store_location/*=false*/) { // // Get info for a file in the working directory by index // -void CardReader::selectFileByIndex(const uint16_t nr) { +void CardReader::selectFileByIndex(const int16_t nr) { #if ENABLED(SDSORT_CACHE_NAMES) if (nr < sort_count) { strcpy(filename, sortshort[nr]); @@ -928,7 +921,7 @@ void CardReader::selectFileByIndex(const uint16_t nr) { // void CardReader::selectFileByName(const char * const match) { #if ENABLED(SDSORT_CACHE_NAMES) - for (uint16_t nr = 0; nr < sort_count; nr++) + for (int16_t nr = 0; nr < sort_count; nr++) if (strcasecmp(match, sortshort[nr]) == 0) { strcpy(filename, sortshort[nr]); strcpy(longFilename, sortnames[nr]); @@ -941,11 +934,6 @@ void CardReader::selectFileByName(const char * const match) { selectByName(workDir, match); } -uint16_t CardReader::countFilesInWorkDir() { - workDir.rewind(); - return countItems(workDir); -} - /** * Dive to the given DOS 8.3 file path, with optional echo of the dive paths. * @@ -1058,6 +1046,7 @@ void CardReader::cd(const char * relpath) { flag.workDirIsRoot = false; if (workDirDepth < MAX_DIR_DEPTH) workDirParents[workDirDepth++] = workDir; + nrFiles = -1; TERN_(SDCARD_SORT_ALPHA, presort()); } else @@ -1066,6 +1055,7 @@ void CardReader::cd(const char * relpath) { int8_t CardReader::cdup() { if (workDirDepth > 0) { // At least 1 dir has been saved + nrFiles = -1; workDir = --workDirDepth ? workDirParents[workDirDepth - 1] : root; // Use parent, or root if none TERN_(SDCARD_SORT_ALPHA, presort()); } @@ -1077,6 +1067,7 @@ void CardReader::cdroot() { workDir = root; flag.workDirIsRoot = true; workDirDepth = 0; + nrFiles = -1; TERN_(SDCARD_SORT_ALPHA, presort()); } @@ -1085,9 +1076,8 @@ void CardReader::cdroot() { /** * Get the name of a file in the working directory by sort-index */ - void CardReader::getfilename_sorted(const uint16_t nr) { - selectFileByIndex(TERN1(SDSORT_GCODE, sort_alpha) && (nr < sort_count) - ? sort_order[nr] : nr); + void CardReader::selectFileByIndexSorted(const int16_t nr) { + selectFileByIndex(TERN1(SDSORT_GCODE, sort_alpha) && (nr < sort_count) ? sort_order[nr] : nr); } #if ENABLED(SDSORT_USES_RAM) @@ -1128,20 +1118,20 @@ void CardReader::cdroot() { * - Most RAM: Buffer the directory and return filenames from RAM */ void CardReader::presort() { - // Throw away old sort index flush_presort(); + int16_t fileCnt = get_num_items(); + // Sorting may be turned off if (TERN0(SDSORT_GCODE, !sort_alpha)) return; // If there are files, sort up to the limit - uint16_t fileCnt = countFilesInWorkDir(); if (fileCnt > 0) { // Never sort more than the max allowed // If you use folders to organize, 20 may be enough - NOMORE(fileCnt, uint16_t(SDSORT_LIMIT)); + NOMORE(fileCnt, int16_t(SDSORT_LIMIT)); // Sort order is always needed. May be static or dynamic. TERN_(SDSORT_DYNAMIC_RAM, sort_order = new uint8_t[fileCnt]); @@ -1181,7 +1171,7 @@ void CardReader::cdroot() { if (fileCnt > 1) { // Init sort order. - for (uint16_t i = 0; i < fileCnt; i++) { + for (int16_t i = 0; i < fileCnt; i++) { sort_order[i] = i; // If using RAM then read all filenames now. #if ENABLED(SDSORT_USES_RAM) @@ -1200,9 +1190,9 @@ void CardReader::cdroot() { } // Bubble Sort - for (uint16_t i = fileCnt; --i;) { + for (int16_t i = fileCnt; --i;) { bool didSwap = false; - uint8_t o1 = sort_order[0]; + int16_t o1 = sort_order[0]; #if DISABLED(SDSORT_USES_RAM) selectFileByIndex(o1); // Pre-fetch the first entry and save it strcpy(name1, longest_filename()); // so the loop only needs one fetch @@ -1211,8 +1201,8 @@ void CardReader::cdroot() { #endif #endif - for (uint16_t j = 0; j < i; ++j) { - const uint16_t o2 = sort_order[j + 1]; + for (int16_t j = 0; j < i; ++j) { + const int16_t o2 = sort_order[j + 1]; // Compare names from the array or just the two buffered names #if ENABLED(SDSORT_USES_RAM) @@ -1270,7 +1260,7 @@ void CardReader::cdroot() { // Using RAM but not keeping names around #if ENABLED(SDSORT_USES_RAM) && DISABLED(SDSORT_CACHE_NAMES) #if ENABLED(SDSORT_DYNAMIC_RAM) - for (uint16_t i = 0; i < fileCnt; ++i) free(sortnames[i]); + for (int16_t i = 0; i < fileCnt; ++i) free(sortnames[i]); TERN_(HAS_FOLDER_SORTING, delete [] isDir); #endif #endif @@ -1313,15 +1303,13 @@ void CardReader::cdroot() { #endif // SDCARD_SORT_ALPHA -uint16_t CardReader::get_num_Files() { +int16_t CardReader::get_num_items() { if (!isMounted()) return 0; - return ( - #if ALL(SDCARD_SORT_ALPHA, SDSORT_USES_RAM, SDSORT_CACHE_NAMES) - nrFiles // no need to access the SD card for filenames - #else - countFilesInWorkDir() - #endif - ); + if (nrFiles < 0) { + workDir.rewind(); + nrFiles = countItems(workDir); + } + return nrFiles; } // diff --git a/Marlin/src/sd/cardreader.h b/Marlin/src/sd/cardreader.h index 47e3c66e475f2..f3f12f73a0fcd 100644 --- a/Marlin/src/sd/cardreader.h +++ b/Marlin/src/sd/cardreader.h @@ -36,12 +36,6 @@ extern const char M23_STR[], M24_STR[]; #endif #endif -#if ENABLED(SDCARD_RATHERRECENTFIRST) && DISABLED(SDCARD_SORT_ALPHA) - #define SD_ORDER(N,C) ((C) - 1 - (N)) -#else - #define SD_ORDER(N,C) N -#endif - #define MAX_DIR_DEPTH 10 // Maximum folder depth #define MAXDIRNAMELENGTH 8 // DOS folder name size #define MAXPATHNAMELENGTH (1 + (MAXDIRNAMELENGTH + 1) * (MAX_DIR_DEPTH) + 1 + FILENAME_LENGTH) // "/" + N * ("ADIRNAME/") + "filename.ext" @@ -110,8 +104,6 @@ class CardReader { #endif #endif - // // // Methods // // // - CardReader(); static void changeMedia(DiskIODriver *_driver) { driver = _driver; } @@ -153,11 +145,10 @@ class CardReader { static void cdroot(); static void cd(const char *relpath); static int8_t cdup(); - static uint16_t countFilesInWorkDir(); - static uint16_t get_num_Files(); + static int16_t get_num_items(); // Select a file - static void selectFileByIndex(const uint16_t nr); + static void selectFileByIndex(const int16_t nr); static void selectFileByName(const char * const match); // (working directory only) // Print job @@ -200,14 +191,16 @@ class CardReader { #if ENABLED(SDCARD_SORT_ALPHA) static void presort(); - static void getfilename_sorted(const uint16_t nr); + static void selectFileByIndexSorted(const int16_t nr); #if ENABLED(SDSORT_GCODE) FORCE_INLINE static void setSortOn(bool b) { sort_alpha = b; presort(); } FORCE_INLINE static void setSortFolders(int i) { sort_folders = i; presort(); } //FORCE_INLINE static void setSortReverse(bool b) { sort_reverse = b; } #endif #else - FORCE_INLINE static void getfilename_sorted(const uint16_t nr) { selectFileByIndex(nr); } + FORCE_INLINE static void selectFileByIndexSorted(const int16_t nr) { + selectFileByIndex(TERN(SDCARD_RATHERRECENTFIRST, get_num_items() - 1 - nr, (nr))); + } #endif static void ls(const uint8_t lsflags); @@ -265,12 +258,13 @@ class CardReader { // static MediaFile root, workDir, workDirParents[MAX_DIR_DEPTH]; static uint8_t workDirDepth; + static int16_t nrFiles; // Cache the total count // // Alphabetical file and folder sorting // #if ENABLED(SDCARD_SORT_ALPHA) - static uint16_t sort_count; // Count of sorted items in the current directory + static int16_t sort_count; // Count of sorted items in the current directory #if ENABLED(SDSORT_GCODE) static bool sort_alpha; // Flag to enable / disable the feature static int sort_folders; // Folder sorting before/none/after @@ -297,7 +291,6 @@ class CardReader { // If using dynamic ram for names, allocate on the heap. #if ENABLED(SDSORT_CACHE_NAMES) - static uint16_t nrFiles; // Cache the total count #if ENABLED(SDSORT_DYNAMIC_RAM) static char **sortshort, **sortnames; #else @@ -342,8 +335,8 @@ class CardReader { // Directory items // static bool is_visible_entity(const dir_t &p OPTARG(CUSTOM_FIRMWARE_UPLOAD, const bool onlyBin=false)); - static int countItems(MediaFile dir); - static void selectByIndex(MediaFile dir, const uint8_t index); + static int16_t countItems(MediaFile dir); + static void selectByIndex(MediaFile dir, const int16_t index); static void selectByName(MediaFile dir, const char * const match); static void printListing( MediaFile parent, const char * const prepend, const uint8_t lsflags