[MORE][CONUTILS] Implement missing features of the MORE command (#3658)

Implement missing features of the MORE command. Special thanks to @HBelusca. CORE-4019
This commit is contained in:
Katayama Hirofumi MZ 2021-06-09 23:30:30 +09:00 committed by GitHub
parent afc27ab1aa
commit b552901df5
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
26 changed files with 1423 additions and 267 deletions

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_BULGARIAN, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Показва данните на екрана, разделени на страници.\n\n\
MORE < [Устройство:][Път]Файлово име\n\
Команда | MORE\n\
MORE [Устройство:][Път]Файлово име\n\n\
[Устройство:][Път]Файлово име Файл, чието съдържание да бъде показано.\n\
Команда\t\t Команда, чийто изход да бъде показан.\n\n\
При въпроса ""-- Продължаване --"" натиснете произволен клавиш, за показаване на следващата страница.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Продължаване --"
IDS_CONTINUE_PROGRESS "-- Продължаване (%d%%) --"
IDS_FILE_ACCESS "Няма достъп до файл %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_CATALAN, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Mostra en pantalla el contingut pàgina per pàgina.\n\n\
MORE < [Unitat:][Ruta]Nom del fitxer\n\
Instrucció | MORE\n\
MORE [Unitat:][Ruta]Nom del fitxer\n\n\
[Unitat:][Ruta]Nom del fitxer Un fitxer, el contingut del qual serà mostrat.\n\
Instrucció\t\t Una instrucció, el resultat de la qual serà mostrada.\n\n\
Al visualitzar ""-- Continua --"" heu de premer qualsevol tecla per visualitzar la següent pàgina.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Continua --"
IDS_CONTINUE_PROGRESS "-- Continua (%d%%) --"
IDS_FILE_ACCESS "No puc accedir al fitxer %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -9,14 +9,34 @@ LANGUAGE LANG_CZECH, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Zobrazí výstup po jednotlivých stránkách na obrazovku.\n\n\
MORE < [Jednotka:][Cesta]Název souboru\n\
Příkaz | MORE\n\
MORE [Jednotka:][Cesta]Název souboru\n\n\
[Jednotka:][Cesta]Název souboru Soubor, jehož obsah bude zobrazen.\n\
Příkaz\t\t Příkaz, jehož výstup bude zobrazen.\n\n\
Při výzvě ""-- Pokračovat --"" lze stisknout libovolnou klávesu\n\
pro zobrazení další stránky.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Pokračovat --"
IDS_CONTINUE_PROGRESS "-- Pokračovat (%d%%) --"
IDS_FILE_ACCESS "Nelze získat přístup k souboru %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,14 +3,34 @@ LANGUAGE LANG_GERMAN, SUBLANG_NEUTRAL
STRINGTABLE
BEGIN
IDS_USAGE "Zeigt Daten seitenweise auf dem Bildschirm an.\n\n\
MORE < [Laufwerk:][Pfad]Dateiname\n\
Befehl | MORE\n\
MORE [Laufwerk:][Pfad]Dateiname\n\n\
[Laufwerk:][Pfad]Dateiname Eine Datei, deren Inhalt angezeigt werden soll.\n\
Befehl\t\t Ein Befehl, dessen Ausgabe angezeigt werden soll.\n\n\
An der Eingabeaufforderung ""-- Fortsetzung --"" kann eine beliebige\n\
Taste gedrückt werden, um die nächste Seite anzuzeigen.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Fortsetzung --"
IDS_CONTINUE_PROGRESS "-- Fortsetzung (%d%%) --"
IDS_FILE_ACCESS "Auf die Datei %s kann nicht zugegriffen werden.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_GREEK, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Εμφανίζει τα δεδομένα σελίδα-παρά-σελίδα στην οθόνη.\n\n\
MORE < [Δίσκος:][Μονοπάτι]Όνομα αρχείου\n\
Εντολή | MORE\n\
MORE [Δίσκος:][Μονοπάτι]Όνομα αρχείου\n\n\
[Δίσκος:][Μονοπάτι]Όνομα αρχείου Το αρχείο, τα δεδομένα του οποίου θα εμφανιστούν.\n\
Εντολή\t\t Η εντολή, της οποίας η έξοδος θα εμφανιστεί.\n\n\
Στη γραμμή εντολών ""-- Συνέχεια --"" μπορείτε να πατήσετε οποιοδήποτε κουμπί για να δείτε την επόμενη σελίδα.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Συνέχεια --"
IDS_CONTINUE_PROGRESS "-- Συνέχεια (%d%%) --"
IDS_FILE_ACCESS "Δεν ήταν δυνατή η προσπέλαση του αρχείου %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
STRINGTABLE
BEGIN
IDS_USAGE "Displays data page-by-page on the screen.\n\n\
MORE < [Drive:][Path]File name\n\
Command | MORE\n\
MORE [Drive:][Path]File name\n\n\
[Drive:][Path]File name A file, whose content shall be displayed.\n\
Command\t\t A command, whose output shall be displayed.\n\n\
At the prompt ""-- Continue --"" you can press any key to show the next page.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Continue --"
IDS_CONTINUE_PROGRESS "-- Continue (%d%%) --"
IDS_FILE_ACCESS "Cannot access the file %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_SPANISH, SUBLANG_NEUTRAL
STRINGTABLE
BEGIN
IDS_USAGE "Muestra datos página por página en la pantalla.\n\n\
MORE < [Unidad:][Ruta]Nombre del archivo\n\
Comando | MORE\n\
MORE [Unidad:][Ruta]Nombre del archivo\n\n\
[Unidad:][Ruta]Nombre del archivo Un archivo, cuyo contenido pueda ser mostrado.\n\
Comando\t\t Un comando, cuya salida pueda ser mostrada.\n\n\
Al visualizar ""-- Continuar --"" presione cualquier tecla para mostrar la siguiente página.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Continuar --"
IDS_CONTINUE_PROGRESS "-- Continuar (%d%%) --"
IDS_FILE_ACCESS "No se puede acceder al fichero %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_ESTONIAN, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Kuvab andmeid lehekülje kaupa ekraanil.\n\n\
MORE < [Draiv:][Tee]Faili nimi\n\
Käsk | MORE\n\
MORE [Draiv:][Tee]Faili nimi\n\n\
[Draiv:][Tee]Faili nimi Fail mille sisu kuvatakse.\n\
Käsk\t\t\t Käsk mille sisu kuvatakse.\n\n\
Küsimusel ""-- Jätka --"" võib vajutada mis tahes klahvi järgmise lehe näitamiseks.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Jätka --"
IDS_CONTINUE_PROGRESS "-- Jätka (%d%%) --"
IDS_FILE_ACCESS "Ei saa ligi failile %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_FRENCH, SUBLANG_NEUTRAL
STRINGTABLE
BEGIN
IDS_USAGE "Affiche les données page par page à l'écran.\n\n\
MORE < [Lecteur:][Chemin]Nom du fichier\n\
Commande | MORE\n\
MORE [Lecteur:][Chemin]Nom du fichier\n\n\
[Lecteur:][Chemin]Nom du fichier Un fichier, dont le contenu sera affiché.\n\
Commande\t\t Une commande, dont la sortie sera affichée.\n\n\
À l'invite ""-- Continuer --"" Vous pouvez appuyer sur n'importe quelle touche pour afficher la page suivante.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Continuer --"
IDS_CONTINUE_PROGRESS "-- Continuer (%d %%) --"
IDS_FILE_ACCESS "Impossible d'accéder au fichier %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_ITALIAN, SUBLANG_NEUTRAL
STRINGTABLE
BEGIN
IDS_USAGE "Visualizza dati una schermata per volta.\n\n\
MORE < [Drive:][Path]File\n\
Comando | MORE\n\
MORE [Drive:][Path]File\n\n\
[Drive:][Path]File Il file da visualizzare.\n\
Comando\t\t Il comando di cui l'output dev'essere visualizzato.\n\n\
Alla richiesta ""-- Continua --"" premere un tasto qualsiasi per visualizzare la pagina successiva.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Continua --"
IDS_CONTINUE_PROGRESS "-- Continua (%d%%) --"
IDS_FILE_ACCESS "Impossibile accedere al file %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -12,16 +12,34 @@ LANGUAGE LANG_LITHUANIAN, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Atvaizduoja duomenis puslapiais.\n\n\
MORE < [Diskas:][Kelias iki bylos]Bylos vardas\n\
Komanda | MORE\n\
MORE [Diskas:][Kelias iki bylos]Bylos vardas\n\n\
[Diskas:][Kelias iki bylos]Bylos vardas Byla, kurios turinys turi būti\n\
atvaizduotas.\n\
Komanda Komanda, kurios rezultatas turi\n\
būti atvaizduotas.\n\n\
Pasirodžius raginimui ""-- Toliau --"" spauskite bet kurį klavišą, kad\n\
pamatytumėte sekantį puslapį.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Toliau --"
IDS_CONTINUE_PROGRESS "-- Toliau (%d%%) --"
IDS_FILE_ACCESS "Nepavyko atverti bylos %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -3,13 +3,34 @@ LANGUAGE LANG_NORWEGIAN, SUBLANG_NEUTRAL
STRINGTABLE
BEGIN
IDS_USAGE "Vis data side-etter-side på skjermen.\n\n\
MORE < [Stasjon:][Mappe]Filnavn\n\
command | MORE\n\
MORE [Stasjon:][Mappe]Filenavn\n\n\
[Stasjon:][Mappe]Filnavn En fil, Velg innhold som skal vises.\n\
Command\t\t En kommando, Velg output som skal vises.\n\n\
At the prompt ""-- Fortsett --"" du kan trykke en tast for å vise neste side.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Fortsett --"
IDS_CONTINUE_PROGRESS "-- Fortsett (%d%%) --"
IDS_FILE_ACCESS "Får ikke tilgang til filen %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -11,13 +11,34 @@ LANGUAGE LANG_POLISH, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Wyświetla dane, podzielone na odcinki o długości ekranu.\n\n\
MORE < [Napęd:][Ścieżka]Nazwa pliku\n\
Polecenie | MORE\n\
MORE [Napęd:][Ścieżka]Nazwa pliku\n\n\
[Napęd:][Ścieżka]Nazwa pliku Plik, którego zawartość ma być wyświetlona.\n\
Polecenie\t\t Polecenie, którego wynik ma być wyświetlony.\n\n\
Po wyświetleniu ""-- Kontynuuj --"" możesz nacisnąć dowolny klawisz, aby przejść do następnej strony.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Kontynuuj --"
IDS_CONTINUE_PROGRESS "-- Kontynuuj (%d%%) --"
IDS_FILE_ACCESS "Brak dostępu do pliku: %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -11,14 +11,34 @@ LANGUAGE LANG_ROMANIAN, SUBLANG_NEUTRAL
STRINGTABLE
BEGIN
IDS_USAGE "Afișează date pe ecran, pagină-cu-pagină.\n\n\
MORE < [Unitate:][Cale]Nume fișier\n\
Comandă | MORE\n\
MORE [Unitate:][Cale]Nume fișier\n\n\
[Unitate:][Cale]Nume fișier Fișierul al cărui conținut va fi afișat.\n\
Comandă Comanda a cărei ieșire va fi afișată.\n\n\
La vederea sugestiei ""-- Continuă --"" veți apăsa o tastă pentru afișarea\n\
următoarei pagini.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Continuă --"
IDS_CONTINUE_PROGRESS "-- Continuă (%d%%) --"
IDS_FILE_ACCESS "Fișierul «%s» nu poate fi accesat!\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -11,13 +11,34 @@ LANGUAGE LANG_RUSSIAN, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Показывать данные постранично заполняя экран.\n\n\
MORE < [диск:][путь]имя_файла\n\
имя_команды | MORE\n\
MORE [диск:][путь]имя_файла\n\n\
[диск:][путь]имя_файла Файл, отображаемый по фрагментам.\n\
имя_команды Команда, вывод которой отображается на экране.\n\n\
При запросе ""-- Продолжить --"" вы можете нажать любую клавишу для отображения следующего экрана.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Продолжить --"
IDS_CONTINUE_PROGRESS "-- Продолжить (%d%%) --"
IDS_FILE_ACCESS "Нет доступа к файлу %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -7,14 +7,34 @@ LANGUAGE LANG_SLOVAK, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Zobrazuje údaje, stránku za stránkou, na obrazovke.\n\n\
MORE < [Jednotka:][Cesta]Názov súboru\n\
Príkaz | MORE\n\
MORE [Jednotka:][Cesta]Názov súboru\n\n\
[Jednotka:][Cesta]Názov súboru Súbor, ktorého obsah má byť zobrazený.\n\
Príkaz\t\t Príkaz, ktorého výstup má byť zobrazený.\n\n\
Pri výzve ""-- Pokračujte --"" môžete stlačiť ľubovoľný kláves\n\
k zobrazeniu nasledujúcej stránky.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Pokračujte --"
IDS_CONTINUE_PROGRESS "-- Pokračujte (%d%%) --"
IDS_FILE_ACCESS "Neviem získať prístup k súboru %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -7,13 +7,34 @@ LANGUAGE LANG_ALBANIAN, SUBLANG_NEUTRAL
STRINGTABLE
BEGIN
IDS_USAGE "Shfaq të dhëna faqe-per-faqe ne ekran.\n\n\
MORE < [Drive:][Path]File name\n\
Komandë | MORE\n\
MORE [Drive:][Path]File name\n\n\
[Drive:][Path]File name Nje dokument, përmbajtja e të cilit do të shfaqet.\n\
Komandë\t\t Nje komande, nxjerrja e te cilit do të shfaqet.\n\n\
At the prompt ""-- Vazhdo --"" ju mund të shtypni çfarëdo butoni për të vazhduar në faqen tjetër.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Vazhdo --"
IDS_CONTINUE_PROGRESS "-- Vazhdo (%d%%) --"
IDS_FILE_ACCESS "Nuk mund të aksesoj dokumentin %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -10,13 +10,34 @@ LANGUAGE LANG_SWEDISH, SUBLANG_NEUTRAL
STRINGTABLE
BEGIN
IDS_USAGE "Visa data sida-efter-sida på skärmen.\n\n\
MORE < [Enhet:][Mapp]Filnamn\n\
Kommando | MORE\n\
MORE [Enhet:][Mapp]Filnamn\n\n\
[Enhet:][Mapp]Filnamn En fil, Välj innehåll som skall visas.\n\
Kommando\t\t Ett kommando, Välj vad som skall visas.\n\n\
vid prompten ""-- Fortsätt --"" du kan trycka valfri knapp för att visa nästa sida.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Fortsätt --"
IDS_CONTINUE_PROGRESS "-- Fortsätt (%d%%) --"
IDS_FILE_ACCESS "Får inte tillgång till filen %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -5,13 +5,34 @@ LANGUAGE LANG_TURKISH, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Görüntülükte veriyi sayfa sayfa görüntüler.\n\n\
MORE < [Sürücü:][Yol]Kütük adı\n\
Komut | MORE\n\
MORE [Sürücü:][Yol]Kütük adı\n\n\
[Sürücü:][Yol]Kütük adı İçeriği görüntülenecek bir kütük.\n\
Komut\t\t Çıkışı görüntülenecek bir komut.\n\n\
İstemde ""-- Sürdür --"" ile bir sonraki sayfayı göstermek için rastgele bir düğmeye basabilirsiniz.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Sürdür --"
IDS_CONTINUE_PROGRESS "-- Sürdür (%%%d) --"
IDS_FILE_ACCESS "%s kütüğüne erişilemiyor.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -10,14 +10,34 @@ LANGUAGE LANG_UKRAINIAN, SUBLANG_DEFAULT
STRINGTABLE
BEGIN
IDS_USAGE "Виводить iнфрмацію поекранно. Використання:\n\n\
MORE < [Диск:][Шлях]Iм'я_файлу\n\
Command | MORE\n\
MORE [Диск:][Шлях]Iм'я_файлу\n\n\
Де:\n\
[Диск:][Шлях]Ім'я_файлу Файл, вмiст якого треба вивести на екран.\n\
Command\t\t Команда, результат роботи якої треба вивести на екран.\n\n\
На запрошення ""-- Далi --"" Ви можете натиснути будь-яку клавiшу щоб побачити наступну сторiнку.\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- Далi --"
IDS_CONTINUE_PROGRESS "-- Далi (%d%%) --"
IDS_FILE_ACCESS "Не можу отримати доступ до файла %s.\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -5,13 +5,34 @@ LANGUAGE LANG_CHINESE, SUBLANG_CHINESE_SIMPLIFIED
STRINGTABLE
BEGIN
IDS_USAGE "在屏幕上一页一页地显示内容。\n\n\
MORE < [驱动器:][路径]文件名\n\
命令 | MORE\n\
MORE [驱动器:][路径]文件名\n\n\
[驱动器:][路径]文件名 一个将要被如此显示内容的文件。\n\
命令\t\t 一个输出将要被如此显示的命令。\n\n\
在 ""-- 继续 --"" 的提示出现时你可以按任意键来显示下一页。\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- 继续 --"
IDS_CONTINUE_PROGRESS "-- 继续 (%d%%) --"
IDS_FILE_ACCESS "无法访问文件 %s。\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -5,13 +5,34 @@ LANGUAGE LANG_CHINESE, SUBLANG_CHINESE_TRADITIONAL
STRINGTABLE
BEGIN
IDS_USAGE "在螢幕上一頁一頁地顯示內容。\n\n\
MORE < [磁碟機:][路徑]檔案名\n\
命令 | MORE\n\
MORE [磁碟機:][路徑]檔案名\n\n\
[磁碟機:][路徑]檔案名 一個將要被如此顯示內容的檔案。\n\
命令\t\t 一個輸出將要被如此顯示的命令。\n\n\
在 ""-- 繼續 --"" 的提示出現時你可以按任意鍵來顯示下一頁。\n"
MORE [options] < [Drive:][Path]Filename\n\
Command | MORE [options]\n\
MORE [options] [Drive:][Path]Filename\n\n\
Options:\n\
/E Enable extended features.\n\
/C Clear screen before displaying page.\n\
/P Expand form-feed characters.\n\
/S Shrink multiple blank lines to a single line.\n\
/Tn Expand tabs to n spaces (default: 8).\n\
+n Start displaying the first file at line n.\n\n\
[Drive:][Path]Filename A file, whose content shall be displayed.\n\
Command A command, whose output shall be displayed.\n\n\
If extended features are enabled, the following commands are available\n\
at ""-- Continue --"" prompt:\n\
P n Display n lines.\n\
S n Skip n lines.\n\
F Display next file.\n\
Q Quit.\n\
? Show help line.\n\
= Show line number.\n\
<Space> Display next page.\n\
<Enter> Display next line.\n"
IDS_CONTINUE "-- 繼續 --"
IDS_CONTINUE_PROGRESS "-- 繼續 (%d%%) --"
IDS_FILE_ACCESS "無法訪問檔案 %s。\n"
IDS_BAD_FLAG "Invalid argument - '%ls'\n"
IDS_CONTINUE_OPTIONS "-- Continue (%d%%) [Options: psfq=<Space><Enter>] --"
IDS_CONTINUE_LINES "-- Continue (%d%%) -- Lines: "
IDS_CONTINUE_LINE_AT "-- Continue (%d%%) [Line:%d] --"
END

View file

@ -1,14 +1,13 @@
/*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS More Command
* FILE: base/applications/cmdutils/more/more.c
* PURPOSE: Displays text stream from STDIN or from an arbitrary number
* of files to STDOUT, with screen capabilities (more than CAT,
* but less than LESS ^^).
* PROGRAMMERS: Paolo Pantaleo
* Timothy Schepens
* Hermes Belusca-Maito (hermes.belusca@sfr.fr)
* Katayama Hirofumi MZ (katayama.hirofumi.mz@gmail.com)
* PROJECT: ReactOS More Command
* LICENSE: GPL-2.0+ (https://spdx.org/licenses/GPL-2.0+)
* PURPOSE: Displays text stream from STDIN or from an arbitrary number
* of files to STDOUT, with screen capabilities (more than CAT,
* but less than LESS ^^).
* COPYRIGHT: Copyright 1999 Paolo Pantaleo
* Copyright 2003 Timothy Schepens
* Copyright 2016-2021 Hermes Belusca-Maito
* Copyright 2021 Katayama Hirofumi MZ
*/
/*
* MORE.C - external command.
@ -27,6 +26,7 @@
#include <windef.h>
#include <winbase.h>
#include <winnt.h>
#include <winnls.h>
#include <winreg.h>
#include <winuser.h>
@ -51,14 +51,100 @@ HANDLE hKeyboard;
/* Enable/Disable extensions */
BOOL bEnableExtensions = TRUE; // FIXME: By default, it should be FALSE.
#define FLAG_HELP (1 << 0)
#define FLAG_E (1 << 1)
#define FLAG_C (1 << 2)
#define FLAG_P (1 << 3)
#define FLAG_S (1 << 4)
#define FLAG_Tn (1 << 5)
#define FLAG_PLUSn (1 << 6)
static DWORD s_dwFlags = 0;
static LONG s_nTabWidth = 8;
static DWORD s_nNextLineNo = 0;
static BOOL s_bPrevLineIsBlank = FALSE;
static UINT s_nPromptID = IDS_CONTINUE_PROGRESS;
static BOOL s_bDoNextFile = FALSE;
static BOOL IsBlankLine(IN PCWCH line, IN DWORD cch)
{
DWORD ich;
WORD wType;
for (ich = 0; ich < cch; ++ich)
{
wType = 0;
GetStringTypeW(CT_CTYPE1, &line[ich], 1, &wType);
if (!(wType & (C1_BLANK | C1_SPACE)))
return FALSE;
}
return TRUE;
}
static BOOL __stdcall
MorePagerLine(
IN OUT PCON_PAGER Pager,
IN PCWCH line,
IN DWORD cch)
{
DWORD ich;
if (s_dwFlags & FLAG_PLUSn) /* Skip lines */
{
if (Pager->lineno < s_nNextLineNo)
{
Pager->dwFlags |= CON_PAGER_FLAG_DONT_OUTPUT;
s_bPrevLineIsBlank = FALSE;
return TRUE; /* Don't output */
}
s_dwFlags &= ~FLAG_PLUSn;
}
if (s_dwFlags & FLAG_S) /* Shrink blank lines */
{
if (IsBlankLine(line, cch))
{
if (s_bPrevLineIsBlank)
{
Pager->dwFlags |= CON_PAGER_FLAG_DONT_OUTPUT;
return TRUE; /* Don't output */
}
for (ich = 0; ich < cch; ++ich)
{
if (line[ich] == L'\n')
{
s_bPrevLineIsBlank = TRUE;
break;
}
}
}
else
{
s_bPrevLineIsBlank = FALSE;
}
}
s_nNextLineNo = 0;
return FALSE; /* Do output */
}
static BOOL
__stdcall
PagePrompt(PCON_PAGER Pager, DWORD Done, DWORD Total)
{
HANDLE hInput = ConStreamGetOSHandle(StdIn);
HANDLE hOutput = ConStreamGetOSHandle(Pager->Screen->Stream);
CONSOLE_SCREEN_BUFFER_INFO csbi;
COORD orgCursorPosition;
DWORD dwMode;
KEY_EVENT_RECORD KeyEvent;
BOOL fCtrl;
DWORD nLines;
WCHAR chSubCommand = 0;
Restart:
nLines = 0;
/*
* Just use the simple prompt if the file being displayed is the STDIN,
@ -88,16 +174,18 @@ PagePrompt(PCON_PAGER Pager, DWORD Done, DWORD Total)
}
else
{
ConResPrintf(Pager->Screen->Stream, IDS_CONTINUE_PROGRESS,
// (dwSumReadChars - Total + Done) * 100 / dwFileSize
(dwSumReadBytes - (Total - Done) *
(dwSumReadBytes / dwSumReadChars)) * 100 / dwFileSize
);
DWORD dwPercent = (dwSumReadBytes - (Total - Done) *
(dwSumReadBytes / dwSumReadChars)) * 100 / dwFileSize;
if (s_nPromptID == IDS_CONTINUE_LINE_AT)
{
ConResPrintf(Pager->Screen->Stream, s_nPromptID, dwPercent, Pager->lineno);
}
else
{
ConResPrintf(Pager->Screen->Stream, s_nPromptID, dwPercent);
}
}
// TODO: Implement prompt read line!
// FIXME: Does not support TTY yet!
s_nPromptID = IDS_CONTINUE_PROGRESS;
/* RemoveBreakHandler */
SetConsoleCtrlHandler(NULL, TRUE);
@ -106,25 +194,98 @@ PagePrompt(PCON_PAGER Pager, DWORD Done, DWORD Total)
dwMode &= ~ENABLE_PROCESSED_INPUT;
SetConsoleMode(hInput, dwMode);
do
// FIXME: Does not support TTY yet!
ConGetScreenInfo(Pager->Screen, &csbi);
orgCursorPosition = csbi.dwCursorPosition;
for (;;)
{
// FIXME: Does not support TTY yet!
// ConInKey(&KeyEvent);
INPUT_RECORD ir;
INPUT_RECORD ir = {0};
DWORD dwRead;
WCHAR ch;
do
{
ReadConsoleInput(hInput, &ir, 1, &dwRead);
}
while ((ir.EventType != KEY_EVENT) || (!ir.Event.KeyEvent.bKeyDown));
/* Got our key, return to caller */
/* Got our key */
KeyEvent = ir.Event.KeyEvent;
/* Ignore any unsupported keyboard press */
if ((KeyEvent.wVirtualKeyCode == VK_SHIFT) ||
(KeyEvent.wVirtualKeyCode == VK_MENU) ||
(KeyEvent.wVirtualKeyCode == VK_CONTROL))
{
continue;
}
/* Ctrl key is pressed? */
fCtrl = !!(KeyEvent.dwControlKeyState & (LEFT_CTRL_PRESSED | RIGHT_CTRL_PRESSED));
/* Ctrl+C or Ctrl+Esc? */
if (fCtrl && ((KeyEvent.wVirtualKeyCode == VK_ESCAPE) ||
(KeyEvent.wVirtualKeyCode == L'C')))
{
chSubCommand = 0;
break;
}
/* If extended features are unavailable, or no
* pending commands, don't do more processing. */
if (!(s_dwFlags & FLAG_E) || (chSubCommand == 0))
break;
ch = KeyEvent.uChar.UnicodeChar;
if (L'0' <= ch && ch <= L'9')
{
nLines *= 10;
nLines += ch - L'0';
ConStreamWrite(Pager->Screen->Stream, &ch, 1);
continue;
}
else if (KeyEvent.wVirtualKeyCode == VK_RETURN)
{
/* Validate the line number */
break;
}
else if (KeyEvent.wVirtualKeyCode == VK_ESCAPE)
{
/* Cancel the current command */
chSubCommand = 0;
break;
}
else if (KeyEvent.wVirtualKeyCode == VK_BACK)
{
if (nLines != 0)
nLines /= 10;
/* Erase the current character */
ConGetScreenInfo(Pager->Screen, &csbi);
if ( (csbi.dwCursorPosition.Y > orgCursorPosition.Y) ||
((csbi.dwCursorPosition.Y == orgCursorPosition.Y) &&
(csbi.dwCursorPosition.X > orgCursorPosition.X)) )
{
if (csbi.dwCursorPosition.X > 0)
{
csbi.dwCursorPosition.X = csbi.dwCursorPosition.X - 1;
}
else if (csbi.dwCursorPosition.Y > 0)
{
csbi.dwCursorPosition.Y = csbi.dwCursorPosition.Y - 1;
csbi.dwCursorPosition.X = (csbi.dwSize.X ? csbi.dwSize.X - 1 : 0);
}
SetConsoleCursorPosition(hOutput, csbi.dwCursorPosition);
ch = L' ';
ConStreamWrite(Pager->Screen->Stream, &ch, 1);
SetConsoleCursorPosition(hOutput, csbi.dwCursorPosition);
}
continue;
}
}
while ((KeyEvent.wVirtualKeyCode == VK_SHIFT) ||
(KeyEvent.wVirtualKeyCode == VK_MENU) ||
(KeyEvent.wVirtualKeyCode == VK_CONTROL));
/* AddBreakHandler */
SetConsoleCtrlHandler(NULL, FALSE);
@ -140,9 +301,8 @@ PagePrompt(PCON_PAGER Pager, DWORD Done, DWORD Total)
ConClearLine(Pager->Screen->Stream);
/* Ctrl+C or Ctrl+Esc: Control Break */
if ((KeyEvent.wVirtualKeyCode == VK_ESCAPE) ||
((KeyEvent.wVirtualKeyCode == L'C') &&
(KeyEvent.dwControlKeyState & (LEFT_CTRL_PRESSED | RIGHT_CTRL_PRESSED))))
if (fCtrl && ((KeyEvent.wVirtualKeyCode == VK_ESCAPE) ||
(KeyEvent.wVirtualKeyCode == L'C')))
{
/* We break, output a newline */
WCHAR ch = L'\n';
@ -150,18 +310,114 @@ PagePrompt(PCON_PAGER Pager, DWORD Done, DWORD Total)
return FALSE;
}
/* 'Q': Quit */
// FIXME: Available only when command extensions are enabled.
if ((KeyEvent.wVirtualKeyCode == L'Q') &&
!(KeyEvent.dwControlKeyState & (LEFT_CTRL_PRESSED | RIGHT_CTRL_PRESSED)))
switch (chSubCommand)
{
/* We break, output a newline */
WCHAR ch = L'\n';
ConStreamWrite(Pager->Screen->Stream, &ch, 1);
return FALSE;
case L'P':
{
/* If we don't display other lines, just restart the prompt */
if (nLines == 0)
{
chSubCommand = 0;
goto Restart;
}
/* Otherwise tell the pager to display them */
Pager->ScrollRows = nLines;
return TRUE;
}
case L'S':
{
s_dwFlags |= FLAG_PLUSn;
s_nNextLineNo = Pager->lineno + nLines;
return TRUE;
}
default:
chSubCommand = 0;
break;
}
return TRUE;
/* If extended features are available */
if (s_dwFlags & FLAG_E)
{
/* Ignore any key presses if Ctrl is pressed */
if (fCtrl)
{
chSubCommand = 0;
goto Restart;
}
/* 'Q': Quit */
if (KeyEvent.wVirtualKeyCode == L'Q')
{
/* We break, output a newline */
WCHAR ch = L'\n';
ConStreamWrite(Pager->Screen->Stream, &ch, 1);
return FALSE;
}
/* 'F': Next file */
if (KeyEvent.wVirtualKeyCode == L'F')
{
s_bDoNextFile = TRUE;
return FALSE;
}
/* '?': Show Options */
if (KeyEvent.uChar.UnicodeChar == L'?')
{
s_nPromptID = IDS_CONTINUE_OPTIONS;
goto Restart;
}
/* [Enter] key: Display one line */
if (KeyEvent.wVirtualKeyCode == VK_RETURN)
{
Pager->ScrollRows = 1;
return TRUE;
}
/* [Space] key: Display one page */
if (KeyEvent.wVirtualKeyCode == VK_SPACE)
{
if (s_dwFlags & FLAG_C)
{
/* Clear the screen */
ConClearScreen(Pager->Screen);
}
return TRUE;
}
/* 'P': Display n lines */
if (KeyEvent.wVirtualKeyCode == L'P')
{
s_nPromptID = IDS_CONTINUE_LINES;
chSubCommand = L'P';
goto Restart;
}
/* 'S': Skip n lines */
if (KeyEvent.wVirtualKeyCode == L'S')
{
s_nPromptID = IDS_CONTINUE_LINES;
chSubCommand = L'S';
goto Restart;
}
/* '=': Show current line number */
if (KeyEvent.uChar.UnicodeChar == L'=')
{
s_nPromptID = IDS_CONTINUE_LINE_AT;
goto Restart;
}
s_nPromptID = IDS_CONTINUE_PROGRESS;
chSubCommand = 0;
goto Restart;
}
else
{
/* Extended features are unavailable: display one page */
return TRUE;
}
}
/*
@ -445,7 +701,6 @@ FileGetString(
return TRUE;
}
static VOID
LoadRegistrySettings(HKEY hKeyRoot)
{
@ -456,7 +711,8 @@ LoadRegistrySettings(HKEY hKeyRoot)
* Buffer big enough to hold the string L"4294967295",
* corresponding to the literal 0xFFFFFFFF (MAXULONG) in decimal.
*/
DWORD Buffer[6];
WCHAR Buffer[sizeof("4294967295")];
C_ASSERT(sizeof(Buffer) >= sizeof(DWORD));
lRet = RegOpenKeyExW(hKeyRoot,
L"Software\\Microsoft\\Command Processor",
@ -471,7 +727,7 @@ LoadRegistrySettings(HKEY hKeyRoot)
L"EnableExtensions",
NULL,
&dwType,
(LPBYTE)&Buffer,
(PBYTE)&Buffer,
&len);
if (lRet == ERROR_SUCCESS)
{
@ -486,6 +742,138 @@ LoadRegistrySettings(HKEY hKeyRoot)
RegCloseKey(hKey);
}
static BOOL IsFlag(PCWSTR param)
{
PCWSTR pch;
PWCHAR endptr;
if (param[0] == L'/')
return TRUE;
if (param[0] == L'+')
{
pch = param + 1;
if (*pch)
{
(void)wcstol(pch, &endptr, 10);
return (*endptr == 0);
}
}
return FALSE;
}
static BOOL ParseArgument(PCWSTR arg, BOOL* pbHasFiles)
{
PWCHAR endptr;
if (arg[0] == L'/')
{
switch (towupper(arg[1]))
{
case L'?':
if (arg[2] == 0)
{
s_dwFlags |= FLAG_HELP;
return TRUE;
}
break;
case L'E':
if (arg[2] == 0)
{
s_dwFlags |= FLAG_E;
return TRUE;
}
break;
case L'C':
if (arg[2] == 0)
{
s_dwFlags |= FLAG_C;
return TRUE;
}
break;
case L'P':
if (arg[2] == 0)
{
s_dwFlags |= FLAG_P;
return TRUE;
}
break;
case L'S':
if (arg[2] == 0)
{
s_dwFlags |= FLAG_S;
return TRUE;
}
break;
case L'T':
if (arg[2] != 0)
{
s_dwFlags |= FLAG_Tn;
s_nTabWidth = wcstol(&arg[2], &endptr, 10);
if (*endptr == 0)
return TRUE;
}
break;
default:
break;
}
}
else if (arg[0] == L'+')
{
if (arg[1] != 0)
{
s_dwFlags |= FLAG_PLUSn;
s_nNextLineNo = wcstol(&arg[1], &endptr, 10) + 1;
if (*endptr == 0)
return TRUE;
}
}
if (IsFlag(arg))
{
ConResPrintf(StdErr, IDS_BAD_FLAG, arg);
return FALSE;
}
else
{
*pbHasFiles = TRUE;
}
return TRUE;
}
static BOOL ParseMoreVariable(BOOL* pbHasFiles)
{
BOOL ret = TRUE;
PWSTR psz;
PWCHAR pch;
DWORD cch;
cch = GetEnvironmentVariableW(L"MORE", NULL, 0);
if (cch == 0)
return TRUE;
psz = (PWSTR)malloc((cch + 1) * sizeof(WCHAR));
if (!psz)
return TRUE;
if (!GetEnvironmentVariableW(L"MORE", psz, cch + 1))
{
free(psz);
return TRUE;
}
for (pch = wcstok(psz, L" "); pch; pch = wcstok(NULL, L" "))
{
ret = ParseArgument(pch, pbHasFiles);
if (!ret)
break;
}
free(psz);
return ret;
}
// INT CommandMore(LPTSTR cmd, LPTSTR param)
int wmain(int argc, WCHAR* argv[])
{
@ -499,12 +887,13 @@ int wmain(int argc, WCHAR* argv[])
ENCODING Encoding;
DWORD SkipBytes = 0;
BOOL HasFiles;
#define FileCacheBufferSize 4096
PVOID FileCacheBuffer = NULL;
PWCHAR StringBuffer = NULL;
DWORD StringBufferLength = 0;
DWORD dwReadBytes, dwReadChars;
DWORD dwReadBytes = 0, dwReadChars = 0;
TCHAR szFullPath[MAX_PATH];
@ -529,13 +918,8 @@ int wmain(int argc, WCHAR* argv[])
/* Load the registry settings */
LoadRegistrySettings(HKEY_LOCAL_MACHINE);
LoadRegistrySettings(HKEY_CURRENT_USER);
// TODO: First, load the "MORE" environment variable and parse it,
// then parse the command-line parameters.
// FIXME: Parse all the remaining parameters.
// Then the file list can be found at the very end.
// FIXME2: Use the PARSER api that can be found in EVENTCREATE.
if (bEnableExtensions)
s_dwFlags |= FLAG_E;
// NOTE: We might try to duplicate the ConOut for read access... ?
hKeyboard = CreateFileW(L"CONIN$", GENERIC_READ|GENERIC_WRITE,
@ -544,7 +928,6 @@ int wmain(int argc, WCHAR* argv[])
FlushConsoleInputBuffer(hKeyboard);
ConStreamSetOSHandle(StdIn, hKeyboard);
FileCacheBuffer = HeapAlloc(GetProcessHeap(), 0, FileCacheBufferSize);
if (!FileCacheBuffer)
{
@ -553,8 +936,31 @@ int wmain(int argc, WCHAR* argv[])
return 1;
}
/* First, load the "MORE" environment variable and parse it,
* then parse the command-line parameters. */
HasFiles = FALSE;
if (!ParseMoreVariable(&HasFiles))
return 1;
for (i = 1; i < argc; i++)
{
if (!ParseArgument(argv[i], &HasFiles))
return 1;
}
if (s_dwFlags & FLAG_HELP)
{
ConResPuts(StdOut, IDS_USAGE);
return 0;
}
Pager.PagerLine = MorePagerLine;
Pager.dwFlags |= CON_PAGER_FLAG_EXPAND_TABS;
if (s_dwFlags & FLAG_P)
Pager.dwFlags |= CON_PAGER_FLAG_EXPAND_FF;
Pager.nTabWidth = s_nTabWidth;
/* Special case where we run 'MORE' without any argument: we use STDIN */
if (argc <= 1)
if (!HasFiles)
{
/*
* Assign STDIN handle to hFile so that the page prompt function will
@ -572,6 +978,7 @@ int wmain(int argc, WCHAR* argv[])
// SetFilePointer(hFile, 0, NULL, FILE_BEGIN);
Encoding = ENCODING_ANSI; // ENCODING_UTF8;
/* Start paging */
bContinue = ConPutsPaging(&Pager, PagePrompt, TRUE, L"");
if (!bContinue)
goto Quit;
@ -596,7 +1003,7 @@ int wmain(int argc, WCHAR* argv[])
StringBuffer, dwReadChars);
/* If we Ctrl-C/Ctrl-Break, stop everything */
if (!bContinue)
goto Quit;
break;
}
while (bRet && dwReadBytes > 0);
goto Quit;
@ -605,6 +1012,9 @@ int wmain(int argc, WCHAR* argv[])
/* We have files: read them and output them to STDOUT */
for (i = 1; i < argc; i++)
{
if (IsFlag(argv[i]))
continue;
GetFullPathNameW(argv[i], ARRAYSIZE(szFullPath), szFullPath, NULL);
hFile = CreateFileW(szFullPath,
GENERIC_READ,
@ -616,7 +1026,7 @@ int wmain(int argc, WCHAR* argv[])
if (hFile == INVALID_HANDLE_VALUE)
{
ConResPrintf(StdErr, IDS_FILE_ACCESS, szFullPath);
continue;
goto Quit;
}
/* We currently do not support files too big */
@ -636,13 +1046,27 @@ int wmain(int argc, WCHAR* argv[])
IsDataUnicode(FileCacheBuffer, dwReadBytes, &Encoding, &SkipBytes);
SetFilePointer(hFile, SkipBytes, NULL, FILE_BEGIN);
/* Reset state for paging */
s_bPrevLineIsBlank = FALSE;
s_nPromptID = IDS_CONTINUE_PROGRESS;
s_bDoNextFile = FALSE;
/* Update the statistics for PagePrompt */
dwSumReadBytes = dwSumReadChars = 0;
/* Start paging */
bContinue = ConPutsPaging(&Pager, PagePrompt, TRUE, L"");
if (!bContinue)
{
/* We stop displaying this file */
CloseHandle(hFile);
if (s_bDoNextFile)
{
/* Bail out and continue with the other files */
continue;
}
/* We Ctrl-C/Ctrl-Break, stop everything */
goto Quit;
}
@ -655,8 +1079,8 @@ int wmain(int argc, WCHAR* argv[])
if (!bRet || dwReadBytes == 0 || dwReadChars == 0)
{
/*
* We failed at reading the file, bail out and
* continue with the other files.
* We failed at reading the file, bail out
* and continue with the other files.
*/
break;
}
@ -675,16 +1099,28 @@ int wmain(int argc, WCHAR* argv[])
bContinue = ConWritePaging(&Pager, PagePrompt, FALSE,
StringBuffer, dwReadChars);
}
/* If we Ctrl-C/Ctrl-Break, stop everything */
if (!bContinue)
{
CloseHandle(hFile);
goto Quit;
/* We stop displaying this file */
break;
}
}
while (bRet && dwReadBytes > 0);
CloseHandle(hFile);
/* Check whether we should stop displaying this file */
if (!bContinue)
{
if (s_bDoNextFile)
{
/* Bail out and continue with the other files */
continue;
}
/* We Ctrl-C/Ctrl-Break, stop everything */
goto Quit;
}
}
Quit:

View file

@ -4,3 +4,7 @@
#define IDS_CONTINUE 101
#define IDS_CONTINUE_PROGRESS 102
#define IDS_FILE_ACCESS 103
#define IDS_BAD_FLAG 104
#define IDS_CONTINUE_OPTIONS 105
#define IDS_CONTINUE_LINES 106
#define IDS_CONTINUE_LINE_AT 107

View file

@ -2,8 +2,8 @@
* PROJECT: ReactOS Console Utilities Library
* LICENSE: GPL-2.0+ (https://spdx.org/licenses/GPL-2.0+)
* PURPOSE: Console/terminal paging functionality.
* COPYRIGHT: Copyright 2017-2018 ReactOS Team
* Copyright 2017-2018 Hermes Belusca-Maito
* COPYRIGHT: Copyright 2017-2021 Hermes Belusca-Maito
* Copyright 2021 Katayama Hirofumi MZ
*/
/**
@ -21,6 +21,7 @@
#include <winbase.h>
// #include <winnls.h>
#include <wincon.h> // Console APIs (only if kernel32 support included)
#include <winnls.h> // for WideCharToMultiByte
#include <strsafe.h>
#include "conutils.h"
@ -31,7 +32,240 @@
// Temporary HACK
#define CON_STREAM_WRITE ConStreamWrite
#define CP_SHIFTJIS 932 // Japanese Shift-JIS
#define CP_HANGUL 949 // Korean Hangul/Wansung
#define CP_JOHAB 1361 // Korean Johab
#define CP_GB2312 936 // Chinese Simplified (GB2312)
#define CP_BIG5 950 // Chinese Traditional (Big5)
/* IsFarEastCP(CodePage) */
#define IsCJKCodePage(CodePage) \
((CodePage) == CP_SHIFTJIS || (CodePage) == CP_HANGUL || \
/* (CodePage) == CP_JOHAB || */ \
(CodePage) == CP_BIG5 || (CodePage) == CP_GB2312)
static inline INT
GetWidthOfCharCJK(
IN UINT nCodePage,
IN WCHAR ch)
{
INT ret = WideCharToMultiByte(nCodePage, 0, &ch, 1, NULL, 0, NULL, NULL);
if (ret == 0)
ret = 1;
else if (ret > 2)
ret = 2;
return ret;
}
static VOID
ConCallPagerLine(
IN OUT PCON_PAGER Pager,
IN PCTCH line,
IN DWORD cch)
{
Pager->dwFlags &= ~CON_PAGER_FLAG_DONT_OUTPUT; /* Clear the flag */
if (!Pager->PagerLine || !Pager->PagerLine(Pager, line, cch))
CON_STREAM_WRITE(Pager->Screen->Stream, line, cch);
}
static BOOL
ConPagerWorker(IN PCON_PAGER Pager)
{
const DWORD ScreenColumns = Pager->ScreenColumns;
const DWORD ScrollRows = Pager->ScrollRows;
const PCTCH TextBuff = Pager->TextBuff;
const DWORD cch = Pager->cch;
BOOL bFinitePaging = ((ScreenColumns > 0) && (Pager->ScreenRows > 0));
LONG nTabWidth = Pager->nTabWidth;
DWORD ich = Pager->ich;
DWORD iColumn = Pager->iColumn;
DWORD iLine = Pager->iLine;
DWORD lineno = Pager->lineno;
DWORD ichStart = ich;
UINT nCodePage;
BOOL IsCJK;
UINT nWidthOfChar = 1;
BOOL IsDoubleWidthCharTrailing = FALSE;
if (ich >= cch)
return FALSE;
nCodePage = GetConsoleOutputCP();
IsCJK = IsCJKCodePage(nCodePage);
/* Normalize the tab width: if negative or too large,
* cap it to the number of columns. */
if (ScreenColumns > 0) // if (bFinitePaging)
{
if (nTabWidth < 0)
nTabWidth = ScreenColumns - 1;
else
nTabWidth = min(nTabWidth, ScreenColumns - 1);
}
else
{
/* If no column width is known, default to 8 spaces if the
* original value is negative; otherwise keep the current one. */
if (nTabWidth < 0)
nTabWidth = 8;
}
if (Pager->dwFlags & CON_PAGER_FLAG_EXPAND_TABS)
{
ExpandTab:
while (Pager->nSpacePending > 0)
{
/* Stop now if we have displayed more screen lines than requested */
if (bFinitePaging && (iLine >= ScrollRows))
break;
ConCallPagerLine(Pager, L" ", 1);
--(Pager->nSpacePending);
++iColumn;
if ((ScreenColumns > 0) && (iColumn % ScreenColumns == 0))
{
if (!(Pager->dwFlags & CON_PAGER_FLAG_DONT_OUTPUT))
++iLine;
}
}
}
/* Loop over each character in the buffer */
for (; ich < cch; ++ich)
{
/* Stop now if we have displayed more screen lines than requested */
if (bFinitePaging && (iLine >= ScrollRows))
break;
Pager->lineno = lineno;
/* NEWLINE character */
if (TextBuff[ich] == TEXT('\n'))
{
/* Output the pending text, including the newline */
ConCallPagerLine(Pager, &TextBuff[ichStart], ich - ichStart + 1);
ichStart = ich + 1;
if (!(Pager->dwFlags & CON_PAGER_FLAG_DONT_OUTPUT))
++iLine;
iColumn = 0;
/* Done with this line; start a new one */
++lineno;
continue;
}
/* TAB character */
if (TextBuff[ich] == TEXT('\t') &&
(Pager->dwFlags & CON_PAGER_FLAG_EXPAND_TABS))
{
/* Output the pending text */
ConCallPagerLine(Pager, &TextBuff[ichStart], ich - ichStart);
/* Perform tab expansion, unless the tab width is zero */
if (nTabWidth == 0)
{
ichStart = ich + 1;
continue;
}
ichStart = ++ich;
Pager->nSpacePending += nTabWidth - (iColumn % nTabWidth);
goto ExpandTab;
}
/* FORM-FEED character */
if (TextBuff[ich] == TEXT('\f') &&
(Pager->dwFlags & CON_PAGER_FLAG_EXPAND_FF))
{
/* Output the pending text, skipping the form-feed */
ConCallPagerLine(Pager, &TextBuff[ichStart], ich - ichStart);
ichStart = ich + 1;
// FIXME: Should we handle CON_PAGER_FLAG_DONT_OUTPUT ?
if (bFinitePaging)
{
/* Clear until the end of the screen */
while (iLine < ScrollRows)
{
ConCallPagerLine(Pager, L"\n", 1);
// CON_STREAM_WRITE(Pager->Screen->Stream, TEXT("\n"), 1);
// if (!(Pager->dwFlags & CON_PAGER_FLAG_DONT_OUTPUT))
++iLine;
}
}
else
{
/* Just output a FORM-FEED character */
ConCallPagerLine(Pager, L"\f", 1);
// CON_STREAM_WRITE(Pager->Screen->Stream, L"\f", 1);
}
iColumn = 0;
continue;
}
/* Other character - Handle double-width for CJK */
if (IsCJK)
{
nWidthOfChar = GetWidthOfCharCJK(nCodePage, TextBuff[ich]);
if (ScreenColumns > 0)
{
IsDoubleWidthCharTrailing = (nWidthOfChar == 2) &&
((iColumn + 1) % ScreenColumns == 0);
}
}
/* Care about CJK character presentation only when outputting
* to a device where the number of columns is known. */
if (ScreenColumns > 0)
{
if ((iColumn + nWidthOfChar) % ScreenColumns == 0)
{
/* Output the pending text, including the last double-width character */
ConCallPagerLine(Pager, &TextBuff[ichStart], ich - ichStart + 1);
ichStart = ich + 1;
if (!(Pager->dwFlags & CON_PAGER_FLAG_DONT_OUTPUT))
++iLine;
iColumn += nWidthOfChar;
continue;
}
if (IsDoubleWidthCharTrailing)
{
/* Output the pending text, excluding the last double-width character */
ConCallPagerLine(Pager, &TextBuff[ichStart], ich - ichStart);
ichStart = ich;
if (!(Pager->dwFlags & CON_PAGER_FLAG_DONT_OUTPUT))
CON_STREAM_WRITE(Pager->Screen->Stream, TEXT(" "), 1);
--ich;
if (!(Pager->dwFlags & CON_PAGER_FLAG_DONT_OUTPUT))
++iLine;
++iColumn;
continue;
}
}
iColumn += nWidthOfChar;
}
/* Output the remaining text */
if (ich - ichStart > 0)
ConCallPagerLine(Pager, &TextBuff[ichStart], ich - ichStart);
if (iLine >= ScrollRows)
iLine = 0; /* Reset the count of lines being printed */
Pager->ich = ich;
Pager->iColumn = iColumn;
Pager->iLine = iLine;
Pager->lineno = lineno;
return (ich < cch);
}
/* Returns TRUE when all the text is displayed, and FALSE if display is stopped */
BOOL
@ -43,75 +277,80 @@ ConWritePaging(
IN DWORD len)
{
CONSOLE_SCREEN_BUFFER_INFO csbi;
/* Used to see how big the screen is */
DWORD ScreenLines = 0;
/* Chars since start of line */
DWORD CharSL;
DWORD from = 0, i = 0;
BOOL bIsConsole;
/* Parameters validation */
if (!Pager)
return FALSE;
/* Reset LineCount and return if no string has been given */
if (StartPaging == TRUE)
Pager->LineCount = 0;
if (szStr == NULL)
return TRUE;
/* Get the size of the visual screen that can be printed to */
if (!ConGetScreenInfo(Pager->Screen, &csbi))
bIsConsole = ConGetScreenInfo(Pager->Screen, &csbi);
if (bIsConsole)
{
/* Calculate the console screen extent */
Pager->ScreenColumns = csbi.srWindow.Right - csbi.srWindow.Left + 1;
Pager->ScreenRows = csbi.srWindow.Bottom - csbi.srWindow.Top + 1;
}
else
{
/* We assume it's a file handle */
CON_STREAM_WRITE(Pager->Screen->Stream, szStr, len);
return TRUE;
Pager->ScreenColumns = 0;
Pager->ScreenRows = 0;
}
/*
* Get the number of lines currently displayed on screen, minus 1
* to account for the "press any key..." prompt from PagePrompt().
*/
ScreenLines = (csbi.srWindow.Bottom - csbi.srWindow.Top);
CharSL = csbi.dwCursorPosition.X;
/* Make sure the user doesn't have the screen too small */
if (ScreenLines < 4)
if (StartPaging)
{
CON_STREAM_WRITE(Pager->Screen->Stream, szStr, len);
return TRUE;
}
while (i < len)
{
/* Search until the end of a line is reached */
if (szStr[i++] != TEXT('\n') && ++CharSL < csbi.dwSize.X)
continue;
Pager->LineCount++;
CharSL = 0;
if (Pager->LineCount >= ScreenLines)
if (bIsConsole)
{
CON_STREAM_WRITE(Pager->Screen->Stream, &szStr[from], i-from);
from = i;
/* Prompt the user; give him some values for statistics */
// FIXME TODO: The prompt proc can also take ScreenLines ??
if (!PagePrompt(Pager, from, len))
return FALSE;
// TODO: Recalculate 'ScreenLines' in case the user redimensions
// the window during the prompt.
/* Reset the number of lines being printed */
Pager->LineCount = 0;
/* Reset to display one page by default */
Pager->ScrollRows = Pager->ScreenRows - 1;
}
else
{
/* File output: all lines are displayed at once; reset to a default value */
Pager->ScrollRows = 0;
}
}
if (StartPaging)
{
/* Reset the output line count, the column index and the line number */
Pager->iLine = 0;
Pager->iColumn = 0;
Pager->lineno = 1;
Pager->nSpacePending = 0;
}
Pager->TextBuff = szStr;
Pager->cch = len;
Pager->ich = 0;
if (len == 0 || szStr == NULL)
return TRUE;
while (ConPagerWorker(Pager))
{
/* Prompt the user only when we display to a console and the screen
* is not too small: at least one line for the actual paged text and
* one line for the prompt. */
if (bIsConsole && (Pager->ScreenRows >= 2))
{
/* Reset to display one page by default */
Pager->ScrollRows = Pager->ScreenRows - 1;
/* Prompt the user; give him some values for statistics */
if (!PagePrompt(Pager, Pager->ich, Pager->cch))
return FALSE;
}
/* If we display to a console, recalculate its screen extent
* in case the user has redimensioned it during the prompt. */
if (bIsConsole && ConGetScreenInfo(Pager->Screen, &csbi))
{
Pager->ScreenColumns = csbi.srWindow.Right - csbi.srWindow.Left + 1;
Pager->ScreenRows = csbi.srWindow.Bottom - csbi.srWindow.Top + 1;
}
}
if (i > from)
CON_STREAM_WRITE(Pager->Screen->Stream, &szStr[from], i-from);
return TRUE;
}

View file

@ -2,8 +2,8 @@
* PROJECT: ReactOS Console Utilities Library
* LICENSE: GPL-2.0+ (https://spdx.org/licenses/GPL-2.0+)
* PURPOSE: Console/terminal paging functionality.
* COPYRIGHT: Copyright 2017-2018 ReactOS Team
* Copyright 2017-2018 Hermes Belusca-Maito
* COPYRIGHT: Copyright 2017-2021 Hermes Belusca-Maito
* Copyright 2021 Katayama Hirofumi MZ
*/
/**
@ -26,27 +26,50 @@
extern "C" {
#endif
// #include <wincon.h>
struct _CON_PAGER;
typedef BOOL (__stdcall *CON_PAGER_LINE_FN)(
IN OUT struct _CON_PAGER *Pager,
IN PCTCH line,
IN DWORD cch);
/* Flags for CON_PAGER */
#define CON_PAGER_FLAG_DONT_OUTPUT (1 << 0)
#define CON_PAGER_FLAG_EXPAND_TABS (1 << 1)
#define CON_PAGER_FLAG_EXPAND_FF (1 << 2)
typedef struct _CON_PAGER
{
/* Console screen properties */
PCON_SCREEN Screen;
DWORD ScreenColumns;
DWORD ScreenRows;
// TODO: Add more properties. Maybe those extra parameters
// of PAGE_PROMPT could go there?
/* Paging parameters */
CON_PAGER_LINE_FN PagerLine; /* The line function */
LONG nTabWidth;
DWORD ScrollRows;
/* Used to count number of lines since last pause */
DWORD LineCount;
/* Data buffer */
PCTCH TextBuff; /* The text buffer */
DWORD cch; /* The total number of characters */
/* Paging state */
DWORD ich; /* The current index of character */
DWORD iColumn; /* The current index of column */
DWORD iLine; /* The physical output line count of screen */
DWORD lineno; /* The logical line number */
DWORD dwFlags; /* The CON_PAGER_FLAG_... flags */
DWORD nSpacePending;
} CON_PAGER, *PCON_PAGER;
#define INIT_CON_PAGER(pScreen) {(pScreen), 0}
#define InitializeConPager(pPager, pScreen) \
#define InitializeConPager(pPager, pScreen) \
do { \
(pPager)->Screen = (pScreen); \
(pPager)->LineCount = 0; \
ZeroMemory((pPager), sizeof(*(pPager))); \
(pPager)->Screen = (pScreen); \
} while (0)