Page 1 of 1

PrintConsoleAscii Macro

Posted: Thu Oct 08, 2015 4:15 am
by ElementE
Here is a Purebasic macro that will accept a string, either Unicode or Ascii, and write it to the console as an Ascii string (one byte characters).

Code: Select all

Macro PrintConsoleAscii(Text)
*Ptr.Character = @Text
While *Ptr\c
  WriteConsoleData(*Ptr,1)
  *Ptr + SizeOf(Character)
Wend
EndMacro

; test code
OpenConsole()
TestText$="Test String"

PrintConsoleAscii(TestText$)

Input()
This is useful if strings written to the console have to be Ascii strings regardless of whether the program was compiled in Unicode or Ascii mode.

Re: PrintConsoleAscii Macro

Posted: Sun Oct 11, 2015 7:25 am
by ElementE
A new Purebasic function such as PrintConsoleAscii() would be useful when the program's console output is piped to another program that requires Ascii characters only.

Perhaps such a function could be added to Purebasic in the future?

Re: PrintConsoleAscii Macro

Posted: Sun Oct 11, 2015 8:32 am
by Fred
Do you have a concrete example ? On Windows, an unicode program has an unicode console, so if you write ascii to it, it will be all garbage.

Re: PrintConsoleAscii Macro

Posted: Sun Oct 11, 2015 2:49 pm
by ElementE
Here is an example:

Code: Select all

; Program: TestStringToConsole.pb
;
; Purpose: 
; Writes string to Console in Unicode and "Ascii" formats
;
; Notes:
;   1) Create Unicode executable
;   2) Set executable format to "Console"
;   3) Create executable "TestStringToConsole.exe"
;   4) Made with Purebasic v5.31 Windows x86
;
; Usage:
;    1) Open Console Window
;    2) type: TestStringToConsole > test.txt
;
  
; Macro to write only lower byte of Unicode character to console
Macro PrintConsoleAscii(Text)
*Ptr.Character = @Text
While *Ptr\c
  WriteConsoleData(*Ptr,1)
  *Ptr + SizeOf(Character)
Wend
EndMacro

OpenConsole()

TestString.s="Test String to Console"

; write unicode string to console
PrintN("Unicode string:")
PrintN(TestString)

; write lower byte of unicode character only to console
OutText.s="Ascii string:"+#CRLF$
PrintConsoleAscii(OutText)
PrintConsoleAscii(TestString)

CloseConsole()
End
When the output of the program is piped to a text file, and the file is opened in a text editor, the Unicode characters will be represented by two bytes with the upper byte being zero. Opening the "test.txt" file which contains the piped output will display the following:

Code: Select all

U n i c o d e   s t r i n g : 
 
 T e s t   S t r i n g   t o   C o n s o l e 
 
 Ascii string:
Test String to Console


This becomes important when the console program's output is redirected or piped to a file or used as input to another program, for example, in a batch file.
The extra spaces that result when using Unicode characters cause a problem when whatever is receiving the output is expecting only Ascii characters.

Re: PrintConsoleAscii Macro

Posted: Mon Oct 12, 2015 3:16 am
by ElementE
To support console piping of Ascii characters perhaps a new optional argument could be added to the Print and PrintN functions?

Print(Text$ [,Format])
PrintN(Text$ [,Format])

where the optional Format parameter can have one of the values:
#PB_Ascii : Prints the string in ASCII format
#PB_UTF8 : Prints the string in UTF8 format
#PB_Unicode: Prints the string in UTF16 format

If the compiler option is Unicode the default would be #PB_Unicode.

Re: PrintConsoleAscii Macro

Posted: Mon Oct 12, 2015 3:20 am
by Keya
ElementE i would sleep better at night if you build the string first and only call WriteConsoleData once at the end :D

Re: PrintConsoleAscii Macro

Posted: Mon Oct 12, 2015 6:05 am
by Fred
Thanks for the explaination, makes sens to have a flag to Print/N() IMHO