fix spurious size detect error and format error messages from system

TODO: fix unexpanded tilde on Windows
This commit is contained in:
Aaron Liu 2024-02-01 18:18:50 -05:00
parent 497b533010
commit 7b5d7907d1
No known key found for this signature in database
GPG key ID: 2D4DA57B12065A35
2 changed files with 48 additions and 38 deletions

4
.gitignore vendored
View file

@ -47,6 +47,10 @@ x64/
*.vcxproj.* *.vcxproj.*
###Visual Studio Code###
.vscode/
###Java### ###Java###
# Compiled class file # Compiled class file

View file

@ -52,12 +52,16 @@
#ifdef _POSIX_VERSION #ifdef _POSIX_VERSION
// Console output size detection // Console output size detection
#include <sys/ioctl.h> #include <sys/ioctl.h>
// Error explanation, for some reason
#include <cstring>
// Exit codes // Exit codes
#include <sysexits.h> #include <sysexits.h>
#endif #endif
#ifdef _WIN32 #ifdef _WIN32
#include <windows.h> #include <windows.h>
// Error explanation
#include <system_error>
// Following codes copied from /usr/include/sysexits.h, // Following codes copied from /usr/include/sysexits.h,
// license: https://opensource.org/license/BSD-3-clause/ // license: https://opensource.org/license/BSD-3-clause/
@ -626,43 +630,11 @@ enum Mode { AUTO, THUMBNAILS, FULL_SIZE };
int main(int argc, char *argv[]) { int main(int argc, char *argv[]) {
std::ios::sync_with_stdio(false); // apparently makes printing faster std::ios::sync_with_stdio(false); // apparently makes printing faster
bool detectSize = true;
// Platform-specific implementations for determining console size, better
// implementations are welcome
// Fallback sizes when unsuccesful. Sizes are actually 1/4th of the actual // Fallback sizes when unsuccesful. Sizes are actually 1/4th of the actual
int maxWidth = 80; int maxWidth = 80;
int maxHeight = 24; int maxHeight = 24;
#ifdef _POSIX_VERSION
struct winsize w;
// If redirecting STDOUT to one file ( col or row == 0, or the previous
// ioctl call's failed )
if (ioctl(STDOUT_FILENO, TIOCGWINSZ, &w) != 0 ||
(w.ws_col | w.ws_row) == 0) {
std::cerr << "Warning: failed to determine most reasonable size, "
"defaulting to 20x6"
<< std::endl;
} else {
maxWidth = w.ws_col * 4;
maxHeight = w.ws_row * 8;
}
#elif defined _WIN32
CONSOLE_SCREEN_BUFFER_INFO w;
if (GetConsoleScreenBufferInfo(
GetStdHandle(STD_OUTPUT_HANDLE),
&w)) { // just like powershell, but without the hyphens, hooray
maxWidth = w.dwSize.X * 4;
maxHeight = w.dwSize.Y * 8;
} else {
std::cerr
<< "Warning: failed to determine most reasonable size: Error code"
<< GetLastError() << ", defaulting to 20x6" << std::endl;
}
#else
std::cerr << "Warning: failed to determine most reasonable size: "
"unrecognized system, defaulting to 20x6"
<< std::endl;
#endif
// Reading input // Reading input
int8_t flags = 0; // bitwise representation of flags, int8_t flags = 0; // bitwise representation of flags,
@ -675,7 +647,7 @@ int main(int argc, char *argv[]) {
if (argc <= 1) { if (argc <= 1) {
printUsage(); printUsage();
return 0; return EX_USAGE;
} }
for (int i = 1; i < argc; i++) { for (int i = 1; i < argc; i++) {
@ -695,16 +667,16 @@ int main(int argc, char *argv[]) {
mode = FULL_SIZE; mode = FULL_SIZE;
} else if (arg == "-w") { } else if (arg == "-w") {
if (i < argc - 1) { if (i < argc - 1) {
maxWidth = 4 * std::stoi(argv[++i]); maxWidth = 4 * std::stoi(argv[++i]), detectSize = false;
} else { } else {
std::cerr << "Error: -w requires a number" << std::endl; std::cerr << "Error: -w requires a number" << std::endl;
ret = EX_USAGE; ret = EX_USAGE;
} }
} else if (arg == "-h") { } else if (arg == "-h") {
if (i < argc - 1) if (i < argc - 1)
maxHeight = 8 * std::stoi(argv[++i]); maxHeight = 8 * std::stoi(argv[++i]), detectSize = false;
else else
printUsage(); printUsage(); // people might confuse this with help
} else if (arg == "--256" || arg == "-2" || arg == "-256") { } else if (arg == "--256" || arg == "-2" || arg == "-256") {
flags |= FLAG_MODE_256; flags |= FLAG_MODE_256;
} else if (arg == "--help" || arg == "-help") { } else if (arg == "--help" || arg == "-help") {
@ -721,7 +693,7 @@ int main(int argc, char *argv[]) {
if (std::filesystem::is_regular_file(p.path())) if (std::filesystem::is_regular_file(p.path()))
file_names.push_back(p.path().string()); file_names.push_back(p.path().string());
} else { } else {
// Check if file can be opened // Check if file can be opened, @TODO find better way
std::ifstream fin(arg.c_str()); std::ifstream fin(arg.c_str());
if (fin) { if (fin) {
file_names.push_back(arg); file_names.push_back(arg);
@ -734,6 +706,40 @@ int main(int argc, char *argv[]) {
} }
} }
if (detectSize) {
// Platform-specific implementations for determining console size,
// better implementations are welcome
#ifdef _POSIX_VERSION
struct winsize w;
// If redirecting STDOUT to one file ( col or row == 0, or the previous
// ioctl call's failed )
if (ioctl(STDOUT_FILENO, TIOCGWINSZ, &w) != 0 ||
(w.ws_col | w.ws_row) == 0) {
std::cerr << "Warning: failed to determine most reasonable size: "
<< strerror(errno) << ", defaulting to 20x6" << std::endl;
} else {
maxWidth = w.ws_col * 4;
maxHeight = w.ws_row * 8;
}
#elif defined _WIN32
CONSOLE_SCREEN_BUFFER_INFO w;
if (GetConsoleScreenBufferInfo(
GetStdHandle(STD_OUTPUT_HANDLE),
&w)) { // just like powershell, but without the hyphens, hooray
maxWidth = w.dwSize.X * 4;
maxHeight = w.dwSize.Y * 8;
} else {
std::cerr << "Warning: failed to determine most reasonable size: "
<< std::system_category().message(GetLastError())
<< ", defaulting to 20x6" << std::endl;
}
#else
std::cerr << "Warning: failed to determine most reasonable size: "
"unrecognized system, defaulting to 20x6"
<< std::endl;
#endif
}
if (mode == FULL_SIZE || (mode == AUTO && file_names.size() == 1)) { if (mode == FULL_SIZE || (mode == AUTO && file_names.size() == 1)) {
for (const auto &filename : file_names) { for (const auto &filename : file_names) {
try { try {