Sign in Join

Live chat for Free Pascal, Lazarus, Delphi and every Pascal programmer.

Mailing lists / fpc-devel / 2019-07

Some thoughts on multi-line string support, and a possible syntax that I think is perfectly clean and Pascal-ish.

197 messages · 23 people · –

Reply by email Subscribe to this list Your subscription

Read-only archive. Use j and k to move between messages.

Ben Grasset

This has been discussed I think several times in the past, but I thought I'd bring it up once more as it has never made sense to me that FPC happily supports multi-line *comments* of any length, while having no such multi-line equivalent for string literals.

I was fiddling around with what the clearest, easiest-to-parse, and most similar-to-existing-syntaxes way of doing it would be, and came up with this:

const MultiLineString = (##
'The
line
endings
would
be
implicit
here.
This
is
significantly
cleaner
looking
overall
IMO!'
##);

The rationale being: round-bracket-plus-double-pound-sign is an uncommon enough combination of characters that it is highly unlikely to conflict with anything anyone currently has written inside of a string literal, and also relatively similar to the classic round-bracket-plus-apostrophe multi-line-Pascal-comment syntax.

(It could even be reduced to just one pound sign after the opening bracket and before the closing bracket if that was deemed "safe" to do, but I was just trying to play it safe here.)

So the grammar rules would be:

Any instance of (## *must* be immediately followed by a single apostrophe. After that, a string is parsed, line by line, until another single apostrophe is hit. That second apostrophe *must *be immediately followed by ##) and then finally a semicolon to "terminate" everything.

Note that in Lazarus, for example, everything from the opening (## to the closing ##) would be highlighted in blue just as multi-line comments and *unbroken
*string literals currently are, making them stand out nice and clearly.

To compare that directly to the current way of doing multi-line strings:

const SingleLineString =
'No' + sLineBreak +
'implicit' + sLineBreak +
'line' + sLineBreak +
'endings' + sLineBreak +
'are' + sLineBreak +
'currently' + sLineBreak +
'available.' + sLineBreak +
'I' + sLineBreak +
'fail' + sLineBreak +
'to' + sLineBreak +
'see' + sLineBreak +
'how' + sLineBreak +
'this' + sLineBreak +
'syntax' + sLineBreak +
'is' + sLineBreak +
'preferable' + sLineBreak +
'in' + sLineBreak +
'any' + sLineBreak +

  'way.';

I simply don't, personally, see any argument in *favor* of the current way. (Much more "line noise" due to all the apostrophes, addition signs, and "sLineBreaks", and of course no consistent blue syntax highlighting in IDEs, as well as the fact that it's much more difficult to make use of already-formatted-like-you-want-it text that way, and so on.)

Thoughts?

Reply by email

Michael Van Canneyt
to Ben Grasset: This has been discussed I think several times in the past, but I thought I'd bring it up…
Ben Grasset wrote 8 lines
This has been discussed I think several times in the past, but I thought I'd bring it up once more as it has never made sense to me that FPC happily supports multi-line *comments* of any length, while having no such multi-line equivalent for string literals. I was fiddling around with what the clearest, easiest-to-parse, and most similar-to-existing-syntaxes way of doing it would be, and came up with this:

If multiline string support ever makes it into FPC, I hope it will be simpler, with a backtick character: `

Michael.

Reply by email

Marcus Sackrow
to Ben Grasset: This has been discussed I think several times in the past, but I thought I'd bring it up…
Ben Grasset wrote 25 lines
This has been discussed I think several times in the past, but I thought I'd bring it up once more as it has never made sense to me that FPC happily supports multi-line *comments* of any length, while having no such multi-line equivalent for string literals. I was fiddling around with what the clearest, easiest-to-parse, and most similar-to-existing-syntaxes way of doing it would be, and came up with this: const MultiLineString = (##   'The    line    endings    would    be    implicit    here.    This    is    significantly    cleaner    looking    overall    IMO!' ##);

I use an operator overload(not for constants but inside the code) because I'm used to our script engine have the '/' as operator for strings as line break

operator / (a,b: string): string;
operator/(a, b: string): string;
begin
   Result := a + #13#10 + b;
end;
var
   MultiLineString: string;
begin
   MultiLineString :=
     'this'/
     'is'/
     'a'/
     'multiline';
   // or even shorter:
   MultiLineString := 'this'/'is'/'a'/'multiline';
end;

I would like to have such feature, but then with '/' as operator because then you can use that also inside a normal commandline

writeln('1st line'/'second line');

Greetings,
Marcus

Reply by email

Ben Grasset
to Marcus Sackrow
AM Marcus Sackrow wrote
I use an operator overload(not for constants but inside the code) because I'm used to our script engine have the '/' as operator for strings as line break.

That's certainly a neat use of operator overloading! However, I think that it is still rather less clean/readable than what would be possible with "true" unbroken multiline strings.
For really short stuff like your writeln example, also, it's not much different from just doing the following, which is already supported:

writeln('1st line'#13#10'second line');

or

writeln('1st line'#10'second line');

BTW, doing it with an operator like that introduces quite a bit of additional overhead, as the concatenation is no longer done at compile time.

Look at the assembler output here to get an idea.
<https://godbolt.org/#g:!((g:!((g:!((h:codeEditor,i:(j:1,lang:pascal,source:'unit+output%3B%0A%0A%7B$mode+ObjFPC%7D%7B$H%2B%7D%0A%0Ainterface%0A%0Aoperator/(const+a,+b:+string):+string%3B+inline%3B%0Aprocedure+TestMultiLine%3B%0A%0Aimplementation%0A%0Aoperator/(const+a,+b:+string):+string%3B%0Abegin%0A++Result+:%3D+a+%2B+%2313%2310+%2B+b%3B%0Aend%3B%0A%0Aprocedure+TestMultiLine%3B%0Avar%0A++MultiLineString:+string%3B%0Abegin%0A++MultiLineString+:%3D%0A++++!'this!'/%0A++++!'is!'/%0A++++!'a!'/%0A++++!'multiline!'%3B%0A++//+or+even+shorter:%0A++MultiLineString+:%3D+!'this!'/!'is!'/!'a!'/!'multiline!'%3B%0Aend%3B%0A%0Aend.'),l:'5',n:'0',o:'Pascal+source+%231',t:'0')),k:41.17647058823529,l:'4',n:'0',o:'',s:0,t:'0'),(g:!((h:compiler,i:(compiler:fpc304,filters:(b:'0',binary:'1',commentOnly:'0',demangle:'0',directives:'0',execute:'1',intel:'0',libraryCode:'1',trim:'1'),lang:pascal,libs:!(),options:'-O3+-Ci-+-Cr-+-g-+-CX+-XXs',source:1),l:'5',n:'0',o:'x86-64+fpc+3.0.4+(Editor+%231,+Compiler+%231)+Pascal',t:'0')),k:58.82352941176471,l:'4',n:'0',o:'',s:0,t:'0')),l:'2',n:'0',o:'',t:'0')),version:4>

After thinking about it more though I think Michael's backtick suggestion might actually be the best way to go, because of the fact that backticks currently have *no *meaning at all in Pascal, and as such, the compiler could safely directly and immediately assume that any use of them was specifically either the opening or closing of a multiline string.

Reply by email

Marcus Sackrow
to Ben Grasset
Ben Grasset wrote 24 lines
On Wed, Jul 3, 2019 at 10:22 AM Marcus Sackrow < > wrote: I use an operator overload(not for constants but inside the code) because I'm used to our script engine have the '/' as operator for strings as line break. That's certainly a neat use of operator overloading! However, I think that it is still rather less clean/readable than what would be possible with "true" unbroken multiline strings. For really short stuff like your writeln example, also, it's not much different from just doing the following, which is already supported: writeln('1st line'#13#10'second line'); or writeln('1st line'#10'second line'); BTW, doing it with an operator like that introduces quite a bit of additional overhead, as the concatenation is no longer done at compile time.

Sure I meant with that, if a new scheme would be introduced to make multiline strings easier, i would prefer such operator, then as real compiler operator also for constants and so on. Mine is just a workaround. (the operator would also automatically select the right line ending, mabye defined together with decimalseparator in formatsettings)

real multiline strings, I do not like, because they look ugly in a well indented code... so your initial example taken would have an awful lot of spaces in front of all lines, exept the first one.

Greetings,

Marcus

Reply by email

Ryan Joseph
to Ben Grasset: That's certainly a neat use of operator overloading! However, I think that it is still…
On Jul 3, 2019, at 12:53 PM, Ben Grasset wrote: After thinking about it more though I think Michael's backtick suggestion might actually be the best way to go, because of the fact that backticks currently have no meaning at all in Pascal, and as such, the compiler could safely directly and immediately assume that any use of them was specifically either the opening or closing of a multiline string.

What about double quotes? I think those are available and it makes sense.

Regards,
Ryan Joseph

Reply by email

Unknown author
to Ben Grasset: That's certainly a neat use of operator overloading! However, I think that it is still…
Ben Grasset wrote 9 lines
On Wed, Jul 3, 2019 at 10:22 AM Marcus Sackrow wrote: I use an operator overload(not for constants but inside the code) because I'm used to our script engine have the '/' as operator for strings as line break. That's certainly a neat use of operator overloading! However, I think that it is still rather less clean/readable than what would be possible with "true" unbroken multiline strings.

FWIW: it uses the '/' in the traditional *nix form of indicating a line continues on the next line...

[edit before shipping]

oh! oops! nope... that's the '\' character which i would prefer to see but i do like his operator overload and may swipe it for use with the '\' character some time... it appears to fit perfectly for this task ;)

https://www.google.com/search?q=linux+line+continuation+character

NOTE: No off-list assistance is given without prior approval. *Please keep mailing list traffic on the list unless* *a signed and pre-paid contract is in effect with us.*

Reply by email

Michael Van Canneyt
to Ryan Joseph: What about double quotes? I think those are available and it makes sense. Ryan Joseph
Ryan Joseph wrote 11 lines
> On Jul 3, 2019, at 12:53 PM, Ben Grasset wrote: > > After thinking about it more though I think Michael's backtick suggestion > might actually be the best way to go, because of the fact that backticks > currently have no meaning at all in Pascal, and as such, the compiler > could safely directly and immediately assume that any use of them was > specifically either the opening or closing of a multiline string. What about double quotes? I think those are available and it makes sense.

Better not. A backtick has the advantage that it looks like a single quote.

Double quotes shout 'C' and I have a vague suspicion that one day double quotes will come into view to quote identifiers. (like they do e.g. in SQL)

But the main question is: do we actually want a multiline string ? As far as I am concerned, that question needs to be answered first, and for me personally the answer to that is still a resounding "no".

There is also still:
https://bugs.freepascal.org/view.php?id=25536

Michael.

Reply by email

Ryan Joseph
to Michael Van Canneyt
On Jul 3, 2019, at 2:43 PM, Michael Van Canneyt wrote: But the main question is: do we actually want a multiline string ? As far as I am concerned, that question needs to be answered first, and for me personally the answer to that is still a resounding "no".

I would use it for GLSL shaders embedded in code or maybe other scripts like Lua. Why is it a bad thing? Seems like an obvious win to have long strings in Pascal.

Regards,
Ryan Joseph

Reply by email

gabor
to Michael Van Canneyt: Better not. A backtick has the advantage that it looks like a single quote. Double…

W dniu 2019-07-03 o 20:43, Michael Van Canneyt pisze:

But the main question is: do we actually want a multiline string ? As far as I am concerned, that question needs to be answered first, and for me personally the answer to that is still a resounding "no".
I am also against this, but on the other hand, we could extend
{$I}/{$INCLUDE} directive to include file as a string.
E.g:
const
   SomeString = {$INCLUDESTR filename.txt};
var
   S: String = {$INCLUDESTR filename.txt};
begin
   S := {$INCLUDESTR filename.txt};
...

or even:

S := 'blah' + {$INCLUDESTR filename.txt} + 'blah';

Regards,
Michał

Reply by email

Michael Van Canneyt
to gabor
gabor wrote 20 lines
W dniu 2019-07-03 o 20:43, Michael Van Canneyt pisze: > But the main question is: do we actually want a multiline string ? As > far as I am concerned, that question needs to be answered first, and for > me personally the answer to that is still a resounding "no". I am also against this, but on the other hand, we could extend {$I}/{$INCLUDE} directive to include file as a string. E.g: const SomeString = {$INCLUDESTR filename.txt}; var S: String = {$INCLUDESTR filename.txt}; begin S := {$INCLUDESTR filename.txt}; ... or even: S := 'blah' + {$INCLUDESTR filename.txt} + 'blah';

See the bugreport I indicated.

Michael.

Reply by email

Ben Grasset
to Michael Van Canneyt: Better not. A backtick has the advantage that it looks like a single quote. Double…
PM Michael Van Canneyt wrote
But the main question is: do we actually want a multiline string ? As far as I am concerned, that question needs to be answered first, and for me personally the answer to that is still a resounding "no".

Why, though? What makes it so much different / worse than the presence of multi-line comments?

PM Michael Van Canneyt wrote

Does that patch actually accept proper pre-formatted text? Or does it still require everything to be written like

'String' +
'String +
'String' +
'String';

If the latter, than personally I don't see how it's a solution to the overall problem in any way.

Reply by email

Ben Grasset
to gabor: W dniu 2019-07-03 o 20:43, Michael Van Canneyt pisze: I am also against this, but on the…
PM gabor wrote
I am also against this
program Example;

(*
This is a perfectly
normal multi-line
Pascal comment.
*)

const SA = `
This is a multiline
string using hypothetical backticks.
Imagine it was fully syntax-highlighted
like normal strings and the comment
above are.
`;

const SB =
' This is a multiline' + sLineBreak +
' string using the current syntax.' + sLineBreak + ' Do you really' + sLineBreak +
' find this to be' + sLineBreak +
' more readable?';

begin
end.

Reply by email

gabor
to Ben Grasset

W dniu 2019-07-03 o 22:20, Ben Grasset pisze:

Show quoted text 7 lines
const SA = `   This is a multiline   string using hypothetical backticks.   Imagine it was fully syntax-highlighted   like normal strings and the comment   above are. `;

What is the end-of-line character in this case? #13#10, #10 or #13?

Regards,
Michał.

Reply by email

Ben Grasset
to gabor: W dniu 2019-07-03 o 22:20, Ben Grasset pisze: What is the end-of-line character in this…
PM gabor wrote
What is the end-of-line character in this case? #13#10, #10 or #13?

It's whatever the EOL characters in that physical copy of the source file actually are.

For example, currently #13 and #10 directly result in the "string exceeds end of line" error for string constants.
With multi-line strings, they'd just be included like any other character, and the compiler would continue as normal.

Reply by email

Sven Barth
to Ben Grasset: program Example; (* This is a perfectly normal multi-line Pascal comment. *) const SA = `…
Ben Grasset wrote 31 lines
On Wed, Jul 3, 2019 at 3:27 PM gabor < > wrote: I am also against this program Example; (*   This is a perfectly   normal multi-line   Pascal comment. *) const SA = `   This is a multiline   string using hypothetical backticks.   Imagine it was fully syntax-highlighted   like normal strings and the comment   above are. `; const SB = ' This is a multiline' + sLineBreak + ' string using the current syntax.' + sLineBreak + ' Do you really' + sLineBreak + ' find this to be' + sLineBreak + ' more readable?'; begin end.

In case case of readability: most cases of multi line string constants are likely to be embedded scripts (shaders, SQL, whatever) and thus the $INCLUDESTRING directive mentioned in the bug report is much more useable, because it allows you to view the embedded file in its own editor together with syntax hightlighting and possibly code completion.

I'm with Michael here: I see no *need* for a separate syntax for a multi line string. I see however the need for the ability to include multi line text as a string.

Regards,
Sven

Reply by email

Sven Barth
to Ryan Joseph: What does this do and why has it been sitting there since 2014 if it’s useful? Ryan…
Ryan Joseph wrote 7 lines
> On Jul 3, 2019, at 2:43 PM, Michael Van Canneyt wrote: > > There is also still: > https://bugs.freepascal.org/view.php?id=25536 What does this do and why has it been sitting there since 2014 if it’s useful?

There are also still open questions regarding string encoding and such. Feel free to complete the patch or try to find cases that might break it.

Regards,
Sven

Reply by email

Ben Grasset
to Sven Barth: In case case of readability: most cases of multi line string constants are likely to be…

On Wed, Jul 3, 2019 at 5:48 PM Sven Barth via fpc-devel <

Show quoted text 5 lines
wrote: I'm with Michael here: I see no *need* for a separate syntax for a multi line string.

I don't really think the suggested backtick way is different enough from anything that exists to be considered a "separate syntax", though. It's the exact same thing, with a one-character difference at the opening and close of the string.

If anything I see a use for both the IncludeString directive and multi-line strings. IncludeString would be more suitable for scripts and such as you've suggested, but I can think of a lot of places I'd have liked to have multi-lines strings in the source for stuff like help / options / about text in command-line apps.

Reply by email

Ryan Joseph
to Sven Barth: In case case of readability: most cases of multi line string constants are likely to be…
On Jul 3, 2019, at 5:48 PM, Sven Barth via fpc-devel wrote: In case case of readability: most cases of multi line string constants are likely to be embedded scripts (shaders, SQL, whatever) and thus the $INCLUDESTRING directive mentioned in the bug report is much more useable, because it allows you to view the embedded file in its own editor together with syntax hightlighting and possibly code completion.

Why is this any better than just loading the string at runtime? You’re right it’s probably better to have separate files most of the time but it’s nice to just toss things into source files sometimes for quick and dirty stuff.

Regards,
Ryan Joseph

Reply by email

Marco van de Voort
to Michael Van Canneyt: Better not. A backtick has the advantage that it looks like a single quote. Double…

Op 2019-07-03 om 20:43 schreef Michael Van Canneyt:

But the main question is: do we actually want a multiline string ? As far as I am concerned, that question needs to be answered first, and for me personally the answer to that is still a resounding "no".

Me too. Mostly overrated IMHO, and ugly as sin exception on general rules.

Also goes for comments, but those have been in for a long time, so that is a bit moot.

Reply by email

Michael Thompson
to Marcos Douglas B. Santos: +1 That syntax would be perfect. Marcos Douglas
Show quoted text 7 lines
const SA = ` This is a multiline string using hypothetical backticks. Imagine it was fully syntax-highlighted like normal strings and the comment above are. `;

Also +1, though I'm less enthused about the syntax highlighting. That's icing. Multiline strings are what I'm focused on.

Most of my apps either compile long SQL for generating data or long HTML fragments for reporting.

I have 6 units chock full of SQL string fragments alone, and I shudder each time I have to change a SQL.

Turning these fragments into a multitude of separate files doesn't sound fun either, I'll have lost the ability to scroll through the unit trying to find what constant I assigned that particular flavour of that sql...

Glad this topic is being discussed.

Many thanks

Mike

Reply by email

Ben Grasset
to Michael Thompson
PM Michael Thompson wrote
Also +1, though I'm less enthused about the syntax highlighting. That's icing. Multiline strings are what I'm focused on.

Well, the syntax highlighting is quite trivial to implement in SynHighlighterPas in the case of Lazarus. I was just pointing it out to help visualize what it would look like in real life.

Reply by email

Ben Grasset
to Marco van de Voort: Op 2019-07-03 om 20:43 schreef Michael Van Canneyt: Me too. Mostly overrated IMHO, and…
PM Marco van de Voort wrote
Me too. Mostly overrated IMHO, and ugly as sin exception on general rules.

They're not overrated. There's very clear uses.

As far as ugly, are you then saying that the "millions of addition operators" way is somehow less ugly?

We're talking about just.... normal text here. I do not see how it can be "ugly" in any case.

PM Marco van de Voort wrote
Also goes for comments, but those have been in for a long time, so that is a bit moot.

It would be ridiculous if FPC did not support multi-line comments.

Reply by email

Ryan Joseph
to Ben Grasset
Show quoted text 7 lines
On Jul 3, 2019, at 7:22 PM, Ben Grasset wrote: Also goes for comments, but those have been in for a long time, so that is a bit moot. It would be ridiculous if FPC did not support multi-line comments.

I don’t understand these objections either. Who says to themselves that they explicitly want a language that doesn’t support multi-line comments or strings? I use both of these all the time in PHP so it’s really hard to understand why this would be opposed.

Regards,
Ryan Joseph

Reply by email

John Doe
to Ben Grasset: program Example; (* This is a perfectly normal multi-line Pascal comment. *) const SA = `…
PM Ben Grasset wrote 8 lines
const SA = ` This is a multiline string using hypothetical backticks. Imagine it was fully syntax-highlighted like normal strings and the comment above are. `;

That would be great to have! I've definitely wanted something like that many times in my Pascal career.

Don't understand why anyone would be against this... just looks like a regular string pretty much.

Reply by email

Ben Grasset
to Ryan Joseph: I don’t understand these objections either. Who says to themselves that they explicitly…
PM Ryan Joseph wrote 5 lines
I don’t understand these objections either. Who says to themselves that they explicitly want a language that doesn’t support multi-line comments or strings? I use both of these all the time in PHP so it’s really hard to understand why this would be opposed.

Especially with the "backtick" method Michael suggested, I really can't see any downsides to it. It looks like strings look.

Reply by email

J. Gareth Moreton
to Ben Grasset

While I like the idea in principle, one thing that I'm a bit worried about is how whitespace is handled, like what counts for a leading or trailing space in the string when between lines, since Pascal parsers (and those for many other languages) traditionally, I believe, discard everything following the last non-whitespace character in a line.  Also, with the backtick suggestion, what should one do if they wish to include a control character (e.g. a linefeed) or the backtick character itself?

Gareth aka. Kit

P.S. I'm definitely supportive of using the backtick over the regular single quotation mark.  And maybe I'm a purist, but I wish to avoid directly immigrating semantics from C and its descendants!  So Pascal should continue to have its own style, like with the { } comments.

Ben Grasset wrote 15 lines
On Wed, Jul 3, 2019 at 7:32 PM Ryan Joseph < > wrote: I don’t understand these objections either. Who says to themselves that they explicitly want a language that doesn’t support multi-line comments or strings? I use both of these all the time in PHP so it’s really hard to understand why this would be opposed. Especially with the "backtick" method Michael suggested, I really can't see any downsides to it. It looks like strings look. _______________________________________________ fpc-devel maillist - https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-devel

---
This email has been checked for viruses by Avast antivirus software. https://www.avast.com/antivirus

Reply by email

Martin Frb
to J. Gareth Moreton
J. Gareth Moreton wrote 5 lines
 Also, with the backtick suggestion, what should one do if they wish to include a control character (e.g. a linefeed) or the backtick character itself?
answer := `Well, this for ``inline`` backticks
and ` + #9 + `this for other chars`;

Reply by email

Ben Grasset
to J. Gareth Moreton: While I like the idea in principle, one thing that I'm a bit worried about is how…
PM J. Gareth Moreton wrote 8 lines
While I like the idea in principle, one thing that I'm a bit worried about is how whitespace is handled, like what counts for a leading or trailing space in the string when between lines, since Pascal parsers (and those for many other languages) traditionally, I believe, discard everything following the last non-whitespace character in a line. Also, with the backtick suggestion, what should one do if they wish to include a control character (e.g. a linefeed) or the backtick character itself?

I've looked through the sources extensively (and started playing around with a basic implementation, actually.) FPC doesn't care about anything other than #13, #10 when it comes to terminating lines, currently.

For the backtick, it just needs to not intentionally error out on #13 and #10, and instead continue until it hits another backtick.

As far as including the backtick itself, the rough version I have going accepts it the same way a single-quote literal is currently accepted (which is to say, if you want a single quote literal, you have to do four of them in a row. Same applies to the backtick.)

Reply by email

Ben Grasset
to Ben Grasset: This has been discussed I think several times in the past, but I thought I'd bring it up…

Ok, I actually got this working fairly easily (though I'm sure it's not perfect.)

Here's what it looks like in Lazarus, with a patched SynEdit. <https://i.imgur.com/w1veLwg.png> Note how you can even "fold" it!

The program pictured compiles, and runs the way you'd expect it to. Assembler output for the string literal looks like this:

_$TEST$_Ld2:
.ascii "QHelp:\015\012 -h:\015\012 Show this help.\015\012" .ascii " -i:\015\012 Print the letter i for no reason.\015" .ascii "\012\000"

Will make a proper Github fork branch for it sometime soon.

Reply by email

Sven Barth
to Ben Grasset: On Wed, Jul 3, 2019 at 5:48 PM Sven Barth via fpc-devel < I don't really think the…
Ben Grasset wrote 12 lines
On Wed, Jul 3, 2019 at 5:48 PM Sven Barth via fpc-devel < > wrote: I'm with Michael here: I see no *need* for a separate syntax for a multi line string.  I don't really think the suggested backtick way is different enough from anything that exists to be considered a "separate syntax", though. It's the exact same thing, with a one-character difference at the opening and close of the string.

As far as the compiler is concerned it definitely *is* a separate syntax. It's a completely new token that didn't exist before with new code inside the parser. Don't try to sugarcoat it because the difference between an apostrophe and a backtick is optically that small.

Regards,
Sven

Reply by email

Sven Barth
to Ryan Joseph: Why is this any better than just loading the string at runtime? You’re right it’s…
Ryan Joseph wrote 5 lines
> On Jul 3, 2019, at 5:48 PM, Sven Barth via fpc-devel wrote: > > In case case of readability: most cases of multi line string constants are likely to be embedded scripts (shaders, SQL, whatever) and thus the $INCLUDESTRING directive mentioned in the bug report is much more useable, because it allows you to view the embedded file in its own editor together with syntax hightlighting and possibly code completion. Why is this any better than just loading the string at runtime? You’re right it’s probably better to have separate files most of the time but it’s nice to just toss things into source files sometimes for quick and dirty stuff.

Because it's part of the binary then; less stuff to distribute or to get lost. Similar with resources. In fact one could already use {$R ...} to load such files contained in the binary, but loading them is a bit more involved than simply using a string.

Regards,
Sven

Reply by email

Sven Barth
to Martin Frb: answer := `Well, this for ``inline`` backticks and ` + #9 + `this for other chars`;
Martin Frb wrote 8 lines
On 04/07/2019 01:57, J. Gareth Moreton wrote: > >  Also, with the backtick suggestion, what should one do if they wish > to include a control character (e.g. a linefeed) or the backtick > character itself? > answer := `Well, this for ``inline`` backticks and ` + #9 + `this for other chars`;

You're aware that normal strings can handle that also without plusses? ;)

answer := `Well, this for ``inline`` backticks
and `#9`this for other chars`;

Regards,
Sven

Reply by email

Sven Barth
to J. Gareth Moreton: While I like the idea in principle, one thing that I'm a bit worried about is how…
J. Gareth Moreton wrote 10 lines
While I like the idea in principle, one thing that I'm a bit worried about is how whitespace is handled, like what counts for a leading or trailing space in the string when between lines, since Pascal parsers (and those for many other languages) traditionally, I believe, discard everything following the last non-whitespace character in a line.  Also, with the backtick suggestion, what should one do if they wish to include a control character (e.g. a linefeed) or the backtick character itself?

Whitespace is indeed an important point. I myself pay quite some attention to nice identation and with multiline strings that will probably break:

=== code begin ===

const SomeString = `Whatever
                                     bar                                      blubb                                      foobar`;

=== code end ===

That's how I also inline my normal multiline strings that I separate with sLineBreak. However to get the same result with this proposed new feature I'd have to do this:

=== code begin ===

const SomeString = `Whatever
bar
blubb
foobar`;

=== code end ===

Which looks just ugly.

And let's not forget that such strings can also be used inside code sequences, cause it wouldn't make sense to restrict them just to constants:

=== code begin ===

var
   s: string;
begin
   if somecondition then
     s := `Some
Multiline
String`
    else
     s := `Some
other
Multiline
String`;
end.

=== code end ===

Even if one would say that the whitespace at the start of a line is discarded that wouldn't make everyone happy, cause then code like the example Ben showed in his mail from today wouldn't work:

=== code begin ===

const Help = `Help:
  -h:
    Show this help.
  -i:
    Print the letter i for no reason.
`;

=== code end ===

So yes, I'm still against this feature.

Regards,
Sven

Reply by email

Sven Barth
to Marco van de Voort: Op 2019-07-03 om 20:43 schreef Michael Van Canneyt: Me too. Mostly overrated IMHO, and…
Marco van de Voort wrote 12 lines
Op 2019-07-03 om 20:43 schreef Michael Van Canneyt: > > But the main question is: do we actually want a multiline string ? As > far as I am concerned, that question needs to be answered first, and for > me personally the answer to that is still a resounding "no". Me too. Mostly overrated IMHO, and ugly as sin exception on general rules. Also goes for comments, but those have been in for a long time, so that is a bit moot.

You are aware that Pascal contained multi line comments (both "(* ... *)" and "{ ... }") before single line comments "// ... " where added? Though I also don't understand why you think multi line comments are overrated.

Regards,
Sven

Reply by email

J. Gareth Moreton
to Sven Barth
Sven Barth wrote 18 lines
Am 04.07.2019 um 01:00 schrieb Marco van de Voort: > > Op 2019-07-03 om 20:43 schreef Michael Van Canneyt: >> >> But the main question is: do we actually want a multiline string ? >> As far as I am concerned, that question needs to be answered first, >> and for >> me personally the answer to that is still a resounding "no". > > Me too. Mostly overrated IMHO, and ugly as sin exception on general > rules. > > Also goes for comments, but those have been in for a long time, so > that is a bit moot. You are aware that Pascal contained multi line comments (both "(* ... *)" and "{ ... }") before single line comments "// ... " where added? Though I also don't understand why you think multi line comments are overrated.

I always get a nasty emotion comparable to nationalism when I see a feature or formatting style introduced into Pascal just for it to resemble C!  I personally love Pascal's multi-line comments and think they look quite neat in the source file, but that's just me.

Gareth aka. Kit

---
This email has been checked for viruses by Avast antivirus software. https://www.avast.com/antivirus

Reply by email

J. Gareth Moreton
to Sven Barth: Whitespace is indeed an important point. I myself pay quite some attention to nice…
Sven Barth wrote 38 lines
Am 04.07.2019 um 01:57 schrieb J. Gareth Moreton: > > While I like the idea in principle, one thing that I'm a bit worried > about is how whitespace is handled, like what counts for a leading or > trailing space in the string when between lines, since Pascal parsers > (and those for many other languages) traditionally, I believe, > discard everything following the last non-whitespace character in a > line.  Also, with the backtick suggestion, what should one do if they > wish to include a control character (e.g. a linefeed) or the backtick > character itself? > Whitespace is indeed an important point. I myself pay quite some attention to nice identation and with multiline strings that will probably break: === code begin === const SomeString = `Whatever                                      bar                                      blubb                                      foobar`; === code end === That's how I also inline my normal multiline strings that I separate with sLineBreak. However to get the same result with this proposed new feature I'd have to do this: === code begin === const SomeString = `Whatever bar blubb foobar`; === code end === Which looks just ugly.

I can definitely see that being a sticking point for such a feature with no easy way to solve it, except to introduce a $INCLUDESTRINGFILE compiler directive, since if the string is so long that it requires the spanning of multiple lines and not using the existing means of extending a Pascal string onto multiple lines, then it probably should be stored in an external text file to be merged upon compilation.

It's a shame, because I like the feature in principle, but the whitespace problem is a bit of a deal-breaker for me.  Also, things like trailing spaces and the line terminators being either #10 or #10#13 may cause a lot of problems if the string has to be known exactly (e.g. for cryptographic hash generation).

Gareth aka. Kit

---
This email has been checked for viruses by Avast antivirus software. https://www.avast.com/antivirus

Reply by email

Pascal Riekenberg
to J. Gareth Moreton
Show quoted text 60 lines
"J. Gareth Moreton" hat am 4. Juli 2019 um 07:45 geschrieben: On 04/07/2019 06:31, Sven Barth via fpc-devel wrote: > Am 04.07.2019 um 01:57 schrieb J. Gareth Moreton: >> >> While I like the idea in principle, one thing that I'm a bit worried >> about is how whitespace is handled, like what counts for a leading or >> trailing space in the string when between lines, since Pascal parsers >> (and those for many other languages) traditionally, I believe, >> discard everything following the last non-whitespace character in a >> line.  Also, with the backtick suggestion, what should one do if they >> wish to include a control character (e.g. a linefeed) or the backtick >> character itself? >> > Whitespace is indeed an important point. I myself pay quite some > attention to nice identation and with multiline strings that will > probably break: > > === code begin === > > const SomeString = `Whatever >                                      bar >                                      blubb >                                      foobar`; > > === code end === > > That's how I also inline my normal multiline strings that I separate > with sLineBreak. However to get the same result with this proposed new > feature I'd have to do this: > > === code begin === > > const SomeString = `Whatever > bar > blubb > foobar`; > > === code end === > > Which looks just ugly. I can definitely see that being a sticking point for such a feature with no easy way to solve it, except to introduce a $INCLUDESTRINGFILE compiler directive, since if the string is so long that it requires the spanning of multiple lines and not using the existing means of extending a Pascal string onto multiple lines, then it probably should be stored in an external text file to be merged upon compilation. It's a shame, because I like the feature in principle, but the whitespace problem is a bit of a deal-breaker for me.  Also, things like trailing spaces and the line terminators being either #10 or #10#13 may cause a lot of problems if the string has to be known exactly (e.g. for cryptographic hash generation). Gareth aka. Kit

What about a Lazarus-Addon / Codetools extention that generates an old style multi-line string from a selection and the other way around to make old style multi-line strings editable again, so you can keep indention and trailing and leading whitespaces and special characters.

Pascal

Reply by email

Michael Van Canneyt
to Pascal Riekenberg
Pascal Riekenberg wrote 6 lines
> What about a Lazarus-Addon / Codetools extention that generates an old style multi-line string from a selection and the other way around to make old style multi-line strings editable again, so you can keep indention and trailing and leading whitespaces and special characters.

This already exists.

Edit/Multipaste

Michael.

Reply by email

Pascal Riekenberg
to Michael Van Canneyt
Show quoted text 11 lines
Michael Van Canneyt hat am 4. Juli 2019 um 10:43 geschrieben: On Thu, 4 Jul 2019, Pascal Riekenberg wrote: > What about a Lazarus-Addon / Codetools extention that generates an old style > multi-line string from a selection and the other way around to make old style > multi-line strings editable again, so you can keep indention and trailing and > leading whitespaces and special characters. This already exists. Edit/Multipaste

Oh, have never seen this! But i thought of a more convenient shortcut function: a) if i a selection is present: build multi-line string from selection in old style format b) if cursor is inside an old style multi-line string: open simple editor to edit and regenerate multi-line string after editor is closed.

Perhaps a) could be extended/switched to generate external file and insert $INCLUDESTRINGFILE directive.

Pascal

Reply by email

Michael Van Canneyt
to Pascal Riekenberg
Pascal Riekenberg wrote 19 lines
> Michael Van Canneyt hat am 4. Juli 2019 um 10:43 geschrieben: > On Thu, 4 Jul 2019, Pascal Riekenberg wrote: > > What about a Lazarus-Addon / Codetools extention that generates an old style > > multi-line string from a selection and the other way around to make old style > > multi-line strings editable again, so you can keep indention and trailing and > > leading whitespaces and special characters. > > This already exists. > > Edit/Multipaste > Oh, have never seen this! But i thought of a more convenient shortcut function: a) if i a selection is present: build multi-line string from selection in old style format b) if cursor is inside an old style multi-line string: open simple editor to edit and regenerate multi-line string after editor is closed. Perhaps a) could be extended/switched to generate external file and insert $INCLUDESTRINGFILE directive.

Well, first $INCLUDESTRINGFILE must be integrated in the compiler.

I proposed something similar in the past on the lazarus mailing list, to quote a block of text. I need it mainly for SQL statements.

So I am all for this 'extension' :-)

Michael.

Reply by email

Pascal Riekenberg
to Michael Van Canneyt
Show quoted text 29 lines
Michael Van Canneyt hat am 4. Juli 2019 um 11:05 geschrieben: On Thu, 4 Jul 2019, Pascal Riekenberg wrote: >> Michael Van Canneyt hat am 4. Juli 2019 um 10:43 geschrieben: >> On Thu, 4 Jul 2019, Pascal Riekenberg wrote: >> > What about a Lazarus-Addon / Codetools extention that generates an old style >> > multi-line string from a selection and the other way around to make old style >> > multi-line strings editable again, so you can keep indention and trailing and >> > leading whitespaces and special characters. >> >> This already exists. >> >> Edit/Multipaste >> > > Oh, have never seen this! But i thought of a more convenient shortcut function: > a) if i a selection is present: build multi-line string from selection in old style format > b) if cursor is inside an old style multi-line string: open simple editor to edit and > regenerate multi-line string after editor is closed. > > Perhaps a) could be extended/switched to generate external file and insert $INCLUDESTRINGFILE > directive. Well, first $INCLUDESTRINGFILE must be integrated in the compiler.

Sure!

Show quoted text 5 lines
I proposed something similar in the past on the lazarus mailing list, to quote a block of text. I need it mainly for SQL statements. So I am all for this 'extension' :-)

Okay, nice project :-) I'll give it a try. I often need this for SQL, XML and any kind of source code generators (COBOL, shell scripts, ...).

Pascal

Reply by email

Marco van de Voort
to Sven Barth: You are aware that Pascal contained multi line comments (both "(* ... *)" and "{ ... }")…

Op 2019-07-04 om 07:34 schreef Sven Barth via fpc-devel:

Show quoted text 13 lines
>> But the main question is: do we actually want a multiline string ? >> As far as I am concerned, that question needs to be answered first, >> and for >> me personally the answer to that is still a resounding "no". > > Me too. Mostly overrated IMHO, and ugly as sin exception on general > rules. > > Also goes for comments, but those have been in for a long time, so > that is a bit moot. You are aware that Pascal contained multi line comments (both "(* ... *)" and "{ ... }") before single line comments "// ... " where added?

Yes. And also that FPC changed them to nest with same time, which Borland style does not.

Though I also don't understand why you think multi line comments are overrated.

I meant multiline literal strings are overrated as feature, the reasons against multiline literal strings, besides that I'm in general against dialect divergence and complication are:

- not really that often needed. Should every hypothetical need or foreign language feature automatically trigger additonal syntax? IMHO No.

- Quite heavy feature because it burdens the language with a concept that spans lines, with the usual strange errors on wrong lines resulting from it if unbalanced. One of the core things I like about Pascal is that its errors are usually in the right line.

- Basically a shorthand, the solution with + works fine. There also could be $includefileasstring or something, one of the few extensions in recent years that I have been in favor of.

In conclusion:  it is a solution in search of a problem, with bad behaviour in errorhandling (when unbalanced the compiler errors on perfectly fine code in the wrong place after whatever ' closes the unbalanced ) on top of it.

This is why the feature goes against the grain of Pascal IMHO.

Reply by email

Marģers .
to Ben Grasset: program Example; (* This is a perfectly normal multi-line Pascal comment. *) const SA = `…

 

----- Reply to message -----
Subject: Re: [fpc-devel] Some thoughts on
multi-line string support, and a possible syntax
that I think is perfectly clean and Pascal-ish.
Date: trešd., 3 jūl., 23:20
From: Ben Grasset
To: FPC developers' list

Show quoted text 18 lines
program Example; (*   This is a perfectly   normal multi-line   Pascal comment. *) const SA = `   This is a multiline   string using hypothetical backticks.   Imagine it was fully syntax-highlighted   like normal strings and the comment   above are. `; begin end. 

Why introduce ` if there already is ' ? Just use ' as well for multi line strings. For people of more conservative view point, put multilinestring
behind mode switch.

Reply by email

Tomas Hajny
to Marģers .

On 2019-07-04 12:59, Marģers . via fpc-devel wrote:

.
.

Why introduce ` if there already is ' ? Just use ' as well for multi line strings. For people of more conservative view point, put multilinestring behind mode switch.

Because then it's never clear whether the fact that there's no ending quote before the end of the line is an omission, or an intention.

Tomas

Reply by email

Michael Van Canneyt
to Tomas Hajny
Tomas Hajny wrote 11 lines
On 2019-07-04 12:59, Marģers . via fpc-devel wrote: . . > Why introduce ` if there already is ' ? Just use ' > as well for multi line strings. For people of more > conservative view point, put multilinestring > behind mode switch. Because then it's never clear whether the fact that there's no ending quote before the end of the line is an omission, or an intention.

Exactly.
The same goes for all other quote characters.
That's why the directive is a better approach; it is unambigious.

Michael.

Reply by email

Sven Barth
to Michael Van Canneyt

Michael Van Canneyt schrieb am Do., 4. Juli 2019, 13:54:

Show quoted text 20 lines
On Thu, 4 Jul 2019, Tomas Hajny wrote: > On 2019-07-04 12:59, Marģers . via fpc-devel wrote: > > . > . >> Why introduce ` if there already is ' ? Just use ' >> as well for multi line strings. For people of more >> conservative view point, put multilinestring >> behind mode switch. > > Because then it's never clear whether the fact that there's no ending > quote before the end of the line is an omission, or an intention. Exactly. The same goes for all other quote characters. That's why the directive is a better approach; it is unambigious.

That is indeed another significant problem. Though to be fair "missing end." errors aren't that seldom either... (though I agree that we shouldn't add a new variant to trigger that error ;) ).

Regards,
Sven

Reply by email

Sven Barth
to Marco van de Voort: Op 2019-07-04 om 07:34 schreef Sven Barth via fpc-devel: Yes. And also that FPC changed…

Marco van de Voort schrieb am Do., 4. Juli
2019, 12:00:

Show quoted text 26 lines
Op 2019-07-04 om 07:34 schreef Sven Barth via fpc-devel: > >>> But the main question is: do we actually want a multiline string ? >>> As far as I am concerned, that question needs to be answered first, >>> and for >>> me personally the answer to that is still a resounding "no". >> >> Me too. Mostly overrated IMHO, and ugly as sin exception on general >> rules. >> >> Also goes for comments, but those have been in for a long time, so >> that is a bit moot. > You are aware that Pascal contained multi line comments (both "(* ... > *)" and "{ ... }") before single line comments "// ... " where added? Yes. And also that FPC changed them to nest with same time, which Borland style does not. > Though I also don't understand why you think multi line comments are > overrated. I meant multiline literal strings are overrated as feature, the reasons against multiline literal strings, besides that I'm in general against dialect divergence and complication are:

We agree on the multiline strings.

So regarding comments you only meant the nesting support and not multiline comments in general? Cause that's what it sounded like... (Note: I myself definitely like that nesting support)

Regards,
Sven

Reply by email

Marco van de Voort
to Sven Barth

Op 2019-07-04 om 14:22 schreef Sven Barth via fpc-devel:

Show quoted text 7 lines
We agree on the multiline strings. So regarding comments you only meant the nesting support and not multiline comments in general? Cause that's what it sounded like... (Note: I myself definitely like that nesting support)

I didn't mean multiline comments.  As for that: there are advantages to either (Delphi: never have to rebalance, FPC/nested: easier to comment block with comments in it), don't care much which actually.

(if you dislike "I hate mode objfpc rants", look away now)

Except of course that having both is worse than either. You get codebases (sometimes even in one project, since it is a per unit setting) in both varieties, and constantly have to rethink in which mode you are in.

Reply by email

Bernd Oppolzer
to Michael Van Canneyt: Exactly. The same goes for all other quote characters. That's why the directive is a…

I have to admit first, that I did not read all the comments in this thread. But anyway,
I'd like to comment on this. Because I have done Pascal programming for almost 40 years
now and even on platforms that are much older than PCs and machines typically run
by Unix systems, I have a somehow different view.

First of all, there is a good reason why Pascal has a WRITELN procedure; because there are platforms where it is simply not possible to write a special
character like 0x0a to flush an output buffer and start a new output line. On old scientific computers of the 1960s and 1970s, there simply was no such character;
this comes from the teletype heritage of the Unix operating system. Even today there
are platforms (and languages) where it is not possible to write a new line on output
simply by writing a 0x0a char. Only people which have grown up with systems like
MS-DOS and Unix take this as given.

So I doubt that there is a portable solution for multi-line strings in the sense that
strings involve carriage-return characters. If you need such things, you have to find
non-portable solutions (like platform-specific constants: CONST NL_Number = 0x0a; for example
or CONST NL_CHAR = X'0a'; ... if your compiler allow such a notation).

Second:

To split strings in source programs, I strongly suggest a solution where the parts are
terminated on every line; otherwise (with strings left open), you will always have a
problem with trailing and leading blanks. The source code should be format free,
after all.

The simplest solution IMO is: simply close the string on one line and open it on the
next one, like here:

CONST long_string = 'this is a long string '
                    'which occupies '                     'multiple source lines';

if you absolutely need to put line feed characters into such a long string, do it like this:

CONST long_string = 'this is a long string ' x'0a'                     'which occupies ' x'0a'                     'multiple source lines';

This is implemented in my New Stanford Pascal compiler.

Kind regards

Bernd

Michael Van Canneyt wrote 24 lines
On Thu, 4 Jul 2019, Tomas Hajny wrote: > On 2019-07-04 12:59, Marģers . via fpc-devel wrote: > >  . >  . >> Why introduce ` if there already is ' ? Just use ' >> as well for multi line strings. For people of more >> conservative view point, put multilinestring >> behind mode switch. > > Because then it's never clear whether the fact that there's no ending > quote before the end of the line is an omission, or an intention. Exactly. The same goes for all other quote characters. That's why the directive is a better approach; it is unambigious. Michael. _______________________________________________ fpc-devel maillist - https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-devel

Reply by email

Ben Grasset
to Sven Barth: Whitespace is indeed an important point. I myself pay quite some attention to nice…

On Thu, Jul 4, 2019 at 1:32 AM Sven Barth via fpc-devel <

Show quoted text 7 lines
wrote: const SomeString = `Whatever bar blubb foobar`;

You can do:

const SomeString =
`Whatever
bar
blubb
foobar`;

Not that I think the "ugliness" argument makes any sense whatsoever. I regularly come across entire source files that are IMO formatted very poorly. Do I think FPC should somehow detect that fact and not compile them? No, of course not. Multiline strings, like everything in a source file, are exactly what you write them as.

AM J. Gareth Moreton wrote
It's a shame, because I like the feature in principle, but the whitespace problem is a bit of a deal-breaker for me.

There is no "problem." A string, again, *is exactly what you write it as.*

AM J. Gareth Moreton wrote
Also, things like trailing spaces and the line terminators being either #10 or #10#13 may cause a lot of problems if the string has to be known exactly (e.g. for cryptographic hash generation).

This, which is IMO *still* a non-problem in the sense of it should absolutely not be the compiler's duty to babysit and/or police line people's *line endings*, would not even be "solved" by IncludeString as it would still then depend on exactly how an editor *saves* the line endings.

Anyways, regardless of whatever bizarre nitpicky complaints people have here and whether or not anyone wants to merge it into trunk, I fully intend to keep developing this (already working, as I demonstrated!) feature and make the patch available for anyone who does want to use it (which as far as I can tell is a significantly-higher-than-zero number of people.)

Reply by email

Ryan Joseph
to Sven Barth: Whitespace is indeed an important point. I myself pay quite some attention to nice…
On Jul 4, 2019, at 1:31 AM, Sven Barth via fpc-devel wrote: Even if one would say that the whitespace at the start of a line is discarded that wouldn't make everyone happy, cause then code like the example Ben showed in his mail from today wouldn't work:

If you need proper formatting and are not willing to have ugly indentation in code then long strings won’t work. However often white space doesn’t matter so it’s not a because it’s not useful 100% of the time doesn’t mean it’s not useful at all.

==================

program test;
const
  shader = '#version 150
            in vec2 inPosition;
            in vec2 inTexCoord;
            in vec4 inColor;
            in float inUVMap;
            out vec2 vertexTexCoord;
            out float vertexUVMap;
            uniform mat4 fullTransform;
            void main()
            {
              gl_Position = fullTransform * vec4(inPosition, 1, 1);
              vertexTexCoord = inTexCoord;
              vertexUVMap = inUVMap;
            }';
  sqlQuery = 'select
                  distribution_stop_information.unique_id_no as stop_unique_id_no
                  ,distribution_line_items.unique_id_no as line_unique_id_no, stop_name
                  ,stop_address,route_code AS RouteCode, customer_reference
                  ,distribution_line_items.datetime_created, rma_number
              from
                  distribution_stop_information
                  join distribution_line_items on distribution_line_items.unique_id_no = distribution_stop_information.unique_id_no
              where
                  distribution_line_items.datetime_created > '2/22/2017' and customer_no = '91000'';
begin
end.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Marco van de Voort: Op 2019-07-04 om 07:34 schreef Sven Barth via fpc-devel: Yes. And also that FPC changed…
AM Marco van de Voort wrote 8 lines
- Basically a shorthand, the solution with + works fine. There also could be $includefileasstring or something, one of the few extensions in recent years that I have been in favor of. In conclusion: it is a solution in search of a problem, with bad behaviour in errorhandling (when unbalanced the compiler errors on perfectly fine code in the wrong place after whatever ' closes the unbalanced ) on top of it.

The solution with + does NOT work fine for non-trivial things and becomes extremely unwieldy, as many people have clearly expressed, nor is the feature "a solution in search of a problem."

Do you think I would have made this post, and then *literally implemented a basic working version of it myself* if I did not want to specifically use it?

No, of course not. This condescending "I know better than you what your use cases are" attitude people keep expressing in this email chain is rather distasteful, IMO.

Reply by email

Michael Van Canneyt
to Ben Grasset: On Thu, Jul 4, 2019 at 1:32 AM Sven Barth via fpc-devel < You can do: const SomeString =…
Ben Grasset wrote 10 lines
> Also, things like > trailing spaces and the line terminators being either #10 or #10#13 may > cause a lot of problems if the string has to be known exactly (e.g. for > cryptographic hash generation). This, which is IMO *still* a non-problem in the sense of it should absolutely not be the compiler's duty to babysit and/or police line people's *line endings*, would not even be "solved" by IncludeString as it would still then depend on exactly how an editor *saves* the line endings.

That's exactly the advantage of IncludeString : You don't need to care about the line ending of the sources. It can differ from those in the strings, which is going to be a tad difficult in an editor such as lazarus - or most editors in fact
- as they will change the line endings uniformly for the whole file...

Michael.

Reply by email

Marco van de Voort
to Ben Grasset: On Thu, Jul 4, 2019 at 1:32 AM Sven Barth via fpc-devel < You can do: const SomeString =…

Op 2019-07-04 om 15:07 schreef Ben Grasset:

Multiline strings, like everything in a source file, are exactly what you write them as.

Take a large pascal file with several strings. Normal, non multi-line strings.

Now, as a thought experiment, remove the closing ' from one of the strings at the top.

In the case of no multiline string support: error on the line with the missing closing string comment.

With multiline string support (just activated the possibility, assume no multistring lines in the file), error on whatever follows the next '  in the file.

Exact nature and location of the error depending on whatever is in the string. Think of fun cases like that the string finds something like doprocedure (',',',','); and image this happens to you in somebody other's code.

I hope this makes it clear that whatever decision or syntax the discussion ends up with, multiline strings should be turned off by default, and it is wise to only use them in short files. (a kind like resourcestrings are often also collected in a separate unit).

Reply by email

Unknown author
to Pascal Riekenberg: What about a Lazarus-Addon / Codetools extention that generates an old style multi-line…
Pascal Riekenberg wrote
What about a Lazarus-Addon / Codetools extention that generates an old style multi-line string from a selection and the other way around to make old style multi-line strings editable again, so you can keep indention and trailing and leading whitespaces and special characters.

1. not everyone uses lazarus.
2. an addon to do what has been basic since forever?
3. which whitespace do we keep and which is thrown away?

personally speaking, i liked the initial idea but i can now easily see why it is only allowed in source code comments... there's a world of difference between them... in one case, the formatting stays put and doesn't affect anything else... in the other, the formatting and whitespace are important and affect a lot of things...

so yeah, i'm out, too... just too much to farkle around with to make it a viable feature without causing problems of one sort or another...

NOTE: No off-list assistance is given without prior approval. *Please keep mailing list traffic on the list unless* *a signed and pre-paid contract is in effect with us.*

Reply by email

Ben Grasset
to Marco van de Voort: Op 2019-07-04 om 15:07 schreef Ben Grasset: Take a large pascal file with several…
AM Marco van de Voort wrote 9 lines
Take a large pascal file with several strings. Normal, non multi-line strings. Now, as a thought experiment, remove the closing ' from one of the strings at the top. In the case of no multiline string support: error on the line with the missing closing string comment.

That's not even how it works, though. Absolutely nothing is changed about the behaviour of "normal" single-line single-quote strings in the (again, working!) implementation I have of this.

Multiline strings are explicitly and only opened / closed used *backticks*.

Everything about the feature is far more simple than you seem to think it is (which is a big part of why I was able to make it work so quickly.)

Reply by email

Marco van de Voort
to Ben Grasset: On Thu, Jul 4, 2019 at 6:01 AM Marco van de Voort The solution with + does NOT work fine…

Op 2019-07-04 om 15:12 schreef Ben Grasset:

Show quoted text 15 lines
On Thu, Jul 4, 2019 at 6:01 AM Marco van de Voort < > wrote: - Basically a shorthand, the solution with + works fine. There also could be $includefileasstring or something, one of the few extensions in recent years that I have been in favor of. In conclusion:  it is a solution in search of a problem, with bad behaviour in errorhandling (when unbalanced the compiler errors on perfectly fine code in the wrong place after whatever ' closes the unbalanced ) on top of it. The solution with + does NOT work fine for non-trivial things

Increasingly unlikely.

and becomes extremely unwieldy,

Yes. Many things driven to extremes are. But the solution is not always to push for a language feature.

E.g. where in this very long thread do the proponents actually balance the need for a language feature against an IDE feature (to decode a  multiline string in + form into a popup, let user perform edit, and then
+ it again).

Where did the _proponents_ consider downsides as behaviour with unbalanced strings?

Nowhere. It is all about bullying the feature in. "need" + "some other language has it" -> "language feature" must happen. Shortest route, no detractions or other opinions please!

as many people have clearly expressed, nor is the feature "a solution in search of a problem."

And as many have said they don't see it.

Do you think I would have made this post, and then *literally implemented a basic working version of it myself* if I did not want to specifically use it?

I don't know what you are thinking.  But as usual in such discussions, the necessity of the features is heavily inflated just to make a case. I don't buy that.

It's rare, create IDE extensions to do the +ing for you, there are multiple ways.

For some reasons you 100% want to have this language feature and will make the earth rotate around that fact if necessary. I'm not buying it.

Show quoted text 5 lines
No, of course not. This condescending "I know better than you what your use cases are" attitude people keep expressing in this email chain is rather distasteful, IMO.

It is actually friendliness, trying to explain rather than a cold "NO". But the whole thing is so irrational and polarized that this is seen as condescending, apparently.

Reply by email

Marco van de Voort
to Ben Grasset: On Thu, Jul 4, 2019 at 9:14 AM Marco van de Voort That's not even how it works, though.…

Op 2019-07-04 om 15:30 schreef Ben Grasset:

Show quoted text 21 lines
On Thu, Jul 4, 2019 at 9:14 AM Marco van de Voort < > wrote: Take a large pascal file with several strings. Normal, non multi-line strings. Now, as a thought experiment, remove the closing ' from one of the strings at the top. In the case of no multiline string support: error on the line with the missing closing string comment. That's not even how it works, though. Absolutely nothing is changed about the behaviour of "normal" single-line single-quote strings in the (again, working!) implementation I have of this. Multiline strings are explicitly and only opened / closed used *backticks*.

New magic characters in the scanner. Yeah. Really nice (NOT!)

Everything about the feature is far more simple than you seem to think it is (which is a big part of why I was able to make it work so quickly.)

Anyway, do you miss imagination or so?

const
     singleline = ' accidentally not terminated;

  // lots of lines

     singleline2 = '   `this is a legal string with backticks`';

Reply by email

Ben Grasset
to Marco van de Voort
AM Marco van de Voort wrote
New magic characters in the scanner. Yeah. Really nice (NOT!)

It's not magic. It's exactly the same thing as the single quote currently is, but denoting multi-line strings specifically.

AM Marco van de Voort wrote 7 lines
const singleline = ' accidentally not terminated; // lots of lines singleline2 = ' `this is a legal string with backticks`';

You clearly do not understand how it works, still. That would not / does not compile, because the first string, which is *single-line as it always has been*, is indeed unterminated. You'd get "string exceeds end of line."

Reply by email

Ben Grasset
to Unknown author: 1. not everyone uses lazarus. 2. an addon to do what has been basic since forever? 3.…
AM wrote 13 lines
personally speaking, i liked the initial idea but i can now easily see why it is only allowed in source code comments... there's a world of difference between them... in one case, the formatting stays put and doesn't affect anything else... in the other, the formatting and whitespace are important and affect a lot of things... so yeah, i'm out, too... just too much to farkle around with to make it a viable feature without causing problems of one sort or another...

This is like saying "somebody might format a text file in a way that they didn't actually want, and thus, TStringList.LoadFromFile is a bad feature."

Reply by email

Ben Grasset
to Marco van de Voort: Op 2019-07-04 om 15:12 schreef Ben Grasset: Increasingly unlikely. Yes. Many things…
AM Marco van de Voort wrote 12 lines
E.g. where in this very long thread do the proponents actually balance the need for a language feature against an IDE feature (to decode a multiline string in + form into a popup, let user perform edit, and then + it again). Where did the _proponents_ consider downsides as behaviour with unbalanced strings? Nowhere. It is all about bullying the feature in. "need" + "some other language has it" -> "language feature" must happen. Shortest route, no detractions or other opinions please!

The "introduce a convoluted Lazarus CodeTools feature" thing is not an equivalent solution as it *entirely* rules out everyone who does not use Lazarus.

There are no downsides with unbalanced strings. As I keep saying, it doesn't work like that.

Lastly I did not say anything about "some other langauge has it". Sure, they *do*, but that's not part of my reasoning. My reasoning is specifically about increasing the usability of *Pascal.*

Reply by email

Unknown author
to Ben Grasset: This is like saying "somebody might format a text file in a way that they didn't actually…
Ben Grasset wrote 13 lines
On Thu, Jul 4, 2019 at 9:28 AM wrote: personally speaking, i liked the initial idea but i can now easily see why it is only allowed in source code comments... there's a world of difference between them... in one case, the formatting stays put and doesn't affect anything else... in the other, the formatting and whitespace are important and affect a lot of things... so yeah, i'm out, too... just too much to farkle around with to make it a viable feature without causing problems of one sort or another... This is like saying "somebody might format a text file in a way that they didn't actually want, and thus, TStringList.LoadFromFile is a bad feature."

not really... LoadFromFile already exists and has been fleshed out whereas multiline strings don't...

don't get me wrong... i'm not against it if someone wants to develop it but i am stepping back like those VC guys on Shark Tank that invest or not in presented projects hoping to get capital and produce their product or service...

NOTE: No off-list assistance is given without prior approval. *Please keep mailing list traffic on the list unless* *a signed and pre-paid contract is in effect with us.*

Reply by email

Marco van de Voort
to Ben Grasset: On Thu, Jul 4, 2019 at 9:35 AM Marco van de Voort It's not magic. It's exactly the same…

Op 2019-07-04 om 15:47 schreef Ben Grasset:

Show quoted text 25 lines
On Thu, Jul 4, 2019 at 9:35 AM Marco van de Voort < > wrote: New magic characters in the scanner. Yeah. Really nice (NOT!) It's not magic. It's exactly the same thing as the single quote currently is, but denoting multi-line strings specifically. On Thu, Jul 4, 2019 at 9:35 AM Marco van de Voort < > wrote: const      singleline = ' accidentally not terminated;    // lots of lines      singleline2 = '   `this is a legal string with backticks`'; You clearly do not understand how it works, still. That would not / does not compile, because the first string, which is *single-line as it always has been*, is indeed unterminated. You'd get "string exceeds end of line."

You clearly didn't read the message fully. It is not about compiler/not compile, but in the case of not compile what the error is and where.

Reply by email

Ben Grasset
to Marco van de Voort

On Thu, Jul 4, 2019 at 10:09 AM Marco van de Voort <

Show quoted text 5 lines
wrote: You clearly didn't read the message fully. It is not about compiler/not compile, but in the case of not compile what the error is and where.

It occurs at the same place it always has, because the scanner itself is designed is such a way that it literally terminates the compilation process immediately upon encountering "string exceeds end of line." (A very good way of doing it, really. The overall design of the scanner was clearly developed with ease of future extensibility in mind.)

Reply by email

Marco van de Voort
to Ben Grasset

Op 2019-07-04 om 16:25 schreef Ben Grasset:

Show quoted text 13 lines
On Thu, Jul 4, 2019 at 10:09 AM Marco van de Voort < > wrote: You clearly didn't read the message fully. It is not about compiler/not compile, but in the case of not compile what the error is and where. It occurs at the same place it always has, because the scanner itself is designed is such a way that it literally terminates the compilation process immediately upon encountering "string exceeds end of line." (A very good way of doing it, really. The overall design of the scanner was clearly developed with ease of future extensibility in mind.)

True, sorry. Didn't fully change my argument to the backticks.

Reply by email

Ryan Joseph
to Ben Grasset
Show quoted text 5 lines
On Jul 4, 2019, at 10:27 AM, Ben Grasset wrote: Well, I already have, and it literally works (including syntax highlighting support in SynEdit for those who do use Lazarus.) See an earlier comment of mine in this email chain for a screenshot.

Just put it up on GitHub so we can test it. We’re not getting anywhere going back and forth over email.

Regards,
Ryan Joseph

Reply by email

Sven Barth
to Marco van de Voort: Op 2019-07-04 om 16:25 schreef Ben Grasset: True, sorry. Didn't fully change my argument…

Marco van de Voort schrieb am Do., 4. Juli
2019, 16:26:

Show quoted text 18 lines
Op 2019-07-04 om 16:25 schreef Ben Grasset: > On Thu, Jul 4, 2019 at 10:09 AM Marco van de Voort > < > wrote: > > You clearly didn't read the message fully. It is not about > compiler/not > compile, but in the case of not compile what the error is and where. > > > It occurs at the same place it always has, because the scanner itself > is designed is such a way that it literally terminates the compilation > process immediately upon encountering "string exceeds end of line." (A > very good way of doing it, really. The overall design of the scanner > was clearly developed with ease of future extensibility in mind.) True, sorry. Didn't fully change my argument to the backticks.

Your argument works if you start with a string that's started with a backtick, but not correctly terminated.

Regards,
Sven

Reply by email

Michael Van Canneyt
to Sven Barth
Sven Barth wrote
Your argument works if you start with a string that's started with a backtick, but not correctly terminated.

To be correct, I think the argument about unterminated line endings needs to be seen for what it is: a nuisance, but not more a nuisance than a mismatched {$IFDEF}.

It is correct that it will be more difficult to determine where it goes wrong. If there are no backticks in the rest of the file, the compiler will reach EOF, and has only the starting line to report.

In case of 2 backtick strings, you will get more difficult situations

for example:

const
a = `this will be unterminated
with
some
lines in it.

Var
   B : String;
begin
   B:=`
again
something
end backticked`;
end.

In this case you will get either a 'Unknown identifier "again"' or 'Semicolon expected"' where the "again" is located or somesuch.

(Ben, what does the patched compiler report in this case ?)

So the compiler will correctly give an error.

The above example will be trivially resolved.
If you have a file of several thousands lines long, the actual error may be located somewhere in these thousands of lines: The error is not 'local', which it definitely is in the case of a simple one-line string.

But as I pointed out:
The same can be said about unbalanced $IFDEFS (the compiler also can only report the first one) and we have that 'feature' too.

IMO the real concern is still clear lack of control of line ending:

Here you are still at the mercy of the settings of the IDE/Editor used, or even the version system you use. If you work in team, someone else's editor can mess up your string without your knowledge.

If the editor of someone else or git replaced CRLF with LF, then this can wreak havoc in windows.

And this can not be waived aside: you must provide an unambiguous solution for this: It definitely is the duty of the compiler to make sure a program behaves consistently, regardless of the whitespace/EOL handling of your editor of choice.

This can be a directive, or whatever, but without a solution for this, the chances of getting multiline strings accepted in the compiler are simply zero.

so e.g. a
{$MULTLINESTRINGLINENDING crlf|cr|lf|platform|raw}

Michael.

Reply by email

Ben Grasset
to Ben Grasset: This has been discussed I think several times in the past, but I thought I'd bring it up…

General implementation question:

The version of this feature I currently have working introduces something of a chicken-and-egg problem while bootstrapping:

The initial version of the compiler being used for the build of course has no knowledge of multi-line strings. Thus, all instances of single-character backtick literals must appear like single-quote-literal / backtick literal / single-quote-literal.

However, once "ppc1" is built, it no longer accepts that, and instead requires the backtick equivalent of the current single-quote-literal syntax (by which I mean, four backticks.)

Currently, I've solved this via an ifdef, however, as there are indeed a number of source files in the FPC codebase besides the compiler where currently single-quote-literal / backtick literal / single-quote-literal appears, it seems like an unwieldy solution.

Would it be better to continue to allow single backticks to appear specifically (and only) inside of *single-line* strings (that is, at any point between two apostrophes)?

I could implement that just as easily, so that's not a concern, and it still would not change the behavior of strings overall in any breaking way.

So it's more a matter of just what people think the overall best way to go about it is.

AM Ben Grasset wrote 78 lines
This has been discussed I think several times in the past, but I thought I'd bring it up once more as it has never made sense to me that FPC happily supports multi-line *comments* of any length, while having no such multi-line equivalent for string literals. I was fiddling around with what the clearest, easiest-to-parse, and most similar-to-existing-syntaxes way of doing it would be, and came up with this: const MultiLineString = (## 'The line endings would be implicit here. This is significantly cleaner looking overall IMO!' ##); The rationale being: round-bracket-plus-double-pound-sign is an uncommon enough combination of characters that it is highly unlikely to conflict with anything anyone currently has written inside of a string literal, and also relatively similar to the classic round-bracket-plus-apostrophe multi-line-Pascal-comment syntax. (It could even be reduced to just one pound sign after the opening bracket and before the closing bracket if that was deemed "safe" to do, but I was just trying to play it safe here.) So the grammar rules would be: Any instance of (## *must* be immediately followed by a single apostrophe. After that, a string is parsed, line by line, until another single apostrophe is hit. That second apostrophe *must *be immediately followed by ##) and then finally a semicolon to "terminate" everything. Note that in Lazarus, for example, everything from the opening (## to the closing ##) would be highlighted in blue just as multi-line comments and *unbroken *string literals currently are, making them stand out nice and clearly. To compare that directly to the current way of doing multi-line strings: const SingleLineString = 'No' + sLineBreak + 'implicit' + sLineBreak + 'line' + sLineBreak + 'endings' + sLineBreak + 'are' + sLineBreak + 'currently' + sLineBreak + 'available.' + sLineBreak + 'I' + sLineBreak + 'fail' + sLineBreak + 'to' + sLineBreak + 'see' + sLineBreak + 'how' + sLineBreak + 'this' + sLineBreak + 'syntax' + sLineBreak + 'is' + sLineBreak + 'preferable' + sLineBreak + 'in' + sLineBreak + 'any' + sLineBreak + 'way.'; I simply don't, personally, see any argument in *favor* of the current way. (Much more "line noise" due to all the apostrophes, addition signs, and "sLineBreaks", and of course no consistent blue syntax highlighting in IDEs, as well as the fact that it's much more difficult to make use of already-formatted-like-you-want-it text that way, and so on.) Thoughts?

Reply by email

Michael Van Canneyt
to Ben Grasset
Ben Grasset wrote 22 lines
General implementation question: The version of this feature I currently have working introduces something of a chicken-and-egg problem while bootstrapping: The initial version of the compiler being used for the build of course has no knowledge of multi-line strings. Thus, all instances of single-character backtick literals must appear like single-quote-literal / backtick literal / single-quote-literal. However, once "ppc1" is built, it no longer accepts that, and instead requires the backtick equivalent of the current single-quote-literal syntax (by which I mean, four backticks.) Currently, I've solved this via an ifdef, however, as there are indeed a number of source files in the FPC codebase besides the compiler where currently single-quote-literal / backtick literal / single-quote-literal appears, it seems like an unwieldy solution. Would it be better to continue to allow single backticks to appear specifically (and only) inside of *single-line* strings (that is, at any point between two apostrophes)?

I would think this is a given...
After all, they are valid characters in a single line string now, that must be kept for backward compatibility.

They should start a multiline string only on the places where a single quote starts a single-line string, i.e. their behaviour is identical to single quote, except that a newline does not terminate them.

Michael.

Reply by email

Ben Grasset
to Michael Van Canneyt
PM Michael Van Canneyt wrote 5 lines
I would think this is a given... After all, they are valid characters in a single line string now, that must be kept for backward compatibility.

That's what I was kind of thinking myself. I just wanted to get an initial working version going to see if I could feasibly do 'll change it to operate like that, then (again, not difficult to implement at all.)

Reply by email

Michael Van Canneyt
to Ben Grasset
Ben Grasset wrote 14 lines
On Thu, Jul 4, 2019 at 12:29 PM Michael Van Canneyt wrote: > I would think this is a given... > After all, they are valid characters in a single line string now, that > must be kept > for backward compatibility. > That's what I was kind of thinking myself. I just wanted to get an initial working version going to see if I could feasibly do it at all. I'll change it to operate like that, then (again, not difficult to implement at all.)

Great.

Please, think of the line-ending issue I pointed out in my last-but-one mail.

Michael.

Reply by email

Marcos Douglas B. Santos
to Sven Barth: Whitespace is indeed an important point. I myself pay quite some attention to nice…
AM Sven Barth wrote 16 lines
[...] Even if one would say that the whitespace at the start of a line is discarded that wouldn't make everyone happy, cause then code like the example Ben showed in his mail from today wouldn't work: === code begin === const Help = `Help: -h: Show this help. -i: Print the letter i for no reason. `; === code end ===

IMHO multiline is to write *code* - like SQL - not a formatted string. But, for formatted string could be:
const Help =
```
Help:
-h:
Show this help.
-i:
Print the letter i for no reason.
```;

Yes, started at the beginning without indentation.

regards,
Marcos Douglas

Reply by email

Marco van de Voort
to Michael Van Canneyt: To be correct, I think the argument about unterminated line endings needs to be seen for…

Op 2019-07-04 om 17:36 schreef Michael Van Canneyt:

Show quoted text 7 lines
> Your argument works if you start with a string that's started with a > backtick, but not correctly terminated. To be correct, I think the argument about unterminated line endings needs to be seen for what it is: a nuisance, but not more a nuisance than a mismatched {$IFDEF}.

If $ifdef was a single char token, maybe. And for a trivial feature, not a core one, like conditional compiling.

So the compiler will correctly give an error.

... but not at or near the place where the mistake is made.

Anyway. I prefer not to have this at all, and would direct this to IDE support. That would also solve the lineending problem, since the ide extension can take care of it.

But whatever decision is made, it should be an modeswitch with off by default.

Reply by email

Ben Grasset
to Michael Van Canneyt: I would think this is a given... After all, they are valid characters in a single line…
PM Michael Van Canneyt wrote 5 lines
I would think this is a given... After all, they are valid characters in a single line string now, that must be kept for backward compatibility.

One more question in this general regard... what would be the most desirable way for the compiler to handle the appearance of a single apostrophe inside a multi-line string?

Of course, it should not terminate it because it's not a backtick. So should it be accepted as a normal character the same way a backtick is accepted within a single-line string? Or should it give some more specific error?

Reply by email

Michael Van Canneyt
to Ben Grasset
Ben Grasset wrote 12 lines
On Thu, Jul 4, 2019 at 12:29 PM Michael Van Canneyt wrote: > I would think this is a given... > After all, they are valid characters in a single line string now, that > must be kept > for backward compatibility. > One more question in this general regard... what would be the most desirable way for the compiler to handle the appearance of a single apostrophe inside a multi-line string?

for reasons of symmetry, if
'`' (quote backtick quote)
is legal, then
`'` (backtick quote backtick)
should also be. I see no point in allowing a normal quote to end a ` string, as the opposite also does not happen. A backtick also does not end a single-quoted string.

The backticked string is in all respects the same as a regular string, except that the single quote delimiter is replaced by a backtick delimiter.

That means that `this is `` a bakcticked string with a backtick in it` should also work.

if memory serves well, Martin Friebe already pointed this out, and IMO rightly so.

Michael.

Reply by email

Zoe Peterson
to Sven Barth: Whitespace is indeed an important point. I myself pay quite some attention to nice…
From: Sven Barth via fpc-devel Whitespace is indeed an important point. I myself pay quite some attention to nice identation and with multiline strings that will probably break:

What about matching Python's whitespace handling for multiline docstrings?

https://www.python.org/dev/peps/pep-0257/#handling-docstring- indentation

"Docstring processing tools will strip a uniform amount of indentation from the second and further lines of the docstring, equal to the minimum indentation of all non-blank lines after the first line. Any indentation in the first line of the docstring (i.e., up to the first newline) is insignificant and removed. Relative indentation of later lines in the docstring is retained. Blank lines should be removed from the beginning and end of the docstring."

Bash heredoc syntax has a similar idea where you can use <<- instead of << to start it to indicate that leading tabs should be ignored.

Zoë Peterson Scooter Software

Reply by email

Ryan Joseph
to Ben Grasset: On Thu, Jul 4, 2019 at 12:29 PM Michael Van Canneyt One more question in this general…
Show quoted text 5 lines
On Jul 4, 2019, at 7:16 PM, Ben Grasset wrote: One more question in this general regard... what would be the most desirable way for the compiler to handle the appearance of a single apostrophe inside a multi-line string? Of course, it should not terminate it because it's not a backtick. So should it be accepted as a normal character the same way a backtick is accepted within a single-line string? Or should it give some more specific error?

I must have missed something, why would a single apostrophe be anything besides just another character? I thought another use of `` strings would be that you don’t need to escape apostrophes using ‘'.

Regards,
Ryan Joseph

Reply by email

Michael Van Canneyt
to Zoe Peterson: What about matching Python's whitespace handling for multiline docstrings?…
Zoe Peterson wrote 9 lines
> From: Sven Barth via fpc-devel > Whitespace is indeed an important point. I myself pay quite some > attention to nice identation and with multiline strings that will > probably break: What about matching Python's whitespace handling for multiline docstrings? https://www.python.org/dev/peps/pep-0257/#handling-docstring-indentation

I was waiting for this proposal to pop up :)

<sarcasm>
"The totally braindead whitespace handling of python in Pascal: over my dead body..." </sarcasm>

No, really not. Pascal does not care about the amount of whitespace. 1 space or 10 does not matter.

Amount of whitespace is and must remain irrelevant. The line-ending is bad enough to deal with, things should not be complicated even further.

Michael.

Reply by email

Ben Grasset
to Ryan Joseph: I must have missed something, why would a single apostrophe be anything besides just…
PM Ryan Joseph wrote
I must have missed something, why would a single apostrophe be anything besides just another character? I thought another use of `` strings would be that you don’t need to escape apostrophes using ‘'.

I didn't really think it should be. Just wanted to make sure we're aiming for the exact "mirror image" of normal strings.

PM Michael Van Canneyt wrote 15 lines
for reasons of symmetry, if '`' (quote backtick quote) is legal, then `'` (backtick quote backtick) should also be. I see no point in allowing a normal quote to end a ` string, as the opposite also does not happen. A backtick also does not end a single-quoted string. The backticked string is in all respects the same as a regular string, except that the single quote delimiter is replaced by a backtick delimiter. That means that `this is `` a bakcticked string with a backtick in it` should also work.

Ok, that's how it already works with the revised version. Just thought I would double-check.

Reply by email

Ben Grasset
to Ben Grasset: This has been discussed I think several times in the past, but I thought I'd bring it up…

Ok, here's a link to my github fork
<https://github.com/Akira13641/freepascal> implementing the multi-line string functionality.

It now includes complete support for user-selected line ending settings, using the directive syntax suggested by Michael.

So, for example, if you view the output of the following program in an editor that can display the line endings directly:

program Example;
{$H+}
{$MULTILINESTRINGLINEENDING CR}

const A =
`
😊
😊
😊
😊
😊
`;

{$MULTILINESTRINGLINEENDING CRLF}

const B =
`
😊
😊
😊
😊
😊
`;

{$MULTILINESTRINGLINEENDING LF}

const C =
`
😊
😊
😊
😊
😊
`;

{$MULTILINESTRINGLINEENDING PLATFORM}

const D =
`
😊
😊
😊
😊
😊
`;

{$MULTILINESTRINGLINEENDING RAW}

const E =
`
😊
😊
😊
😊
😊
`;

begin
  Write(A);
  Write(B);
  Write(C);
  Write(D);
  Write(E);
end.

you'll see that each string adheres to the setting above it. Note that "platform" means whatever line ending your operating system uses, and "raw" means whatever the line endings in the source file itself are. Currently "raw" is the default.

Once I have a set of proper tests written, I suppose I'll submit a formal patch to the FPC bugtracker.

Reply by email

Ben Grasset
to Marco van de Voort: Op 2019-07-04 om 17:36 schreef Michael Van Canneyt: If $ifdef was a single char token,…
PM Marco van de Voort wrote 18 lines
Op 2019-07-04 om 17:36 schreef Michael Van Canneyt: > >> Your argument works if you start with a string that's started with a >> backtick, but not correctly terminated. > > To be correct, I think the argument about unterminated line endings > needs to be seen for what it is: a nuisance, but not more a nuisance > than a mismatched {$IFDEF}. If $ifdef was a single char token, maybe. And for a trivial feature, not a core one, like conditional compiling. > > So the compiler will correctly give an error. ... but not at or near the place where the mistake is made.

I think I can pretty easily make the compiler give an informative error in the specific case of an odd number of backticks.

Something like "Unterminated multi-line string: opened at line ABC, broken by unexpected character at line DEF."

I'll work on this next.

Reply by email

Ben Grasset
to Sven Barth

On Fri, Jul 5, 2019 at 2:02 AM Sven Barth via fpc-devel <

Show quoted text 5 lines
wrote: As stated by I think Michael, a new modeswitch which is by default off is also required.

Ok. {$modeswitch MultiLineStrings} I guess?

Reply by email

Michael Van Canneyt
to Ben Grasset: Ok, here's a link to my github fork <https://github.com/Akira13641/freepascal>…
Ben Grasset wrote 11 lines
Ok, here's a link to my github fork <https://github.com/Akira13641/freepascal> implementing the multi-line string functionality. you'll see that each string adheres to the setting above it. Note that "platform" means whatever line ending your operating system uses, and "raw" means whatever the line endings in the source file itself are. Currently "raw" is the default. Once I have a set of proper tests written, I suppose I'll submit a formal patch to the FPC bugtracker.
Please don't forget the  {$modeswitch multilinestrings};

The switch needs to be off in at lest Delphi/TP mode by default (as these modes must mimic Delphi/TP as closely as possible), and the switch can be used to switch it on for those that want it.

For the rest: nice job, congratulations on a fast implementation!

Michael.

Reply by email

Benito van der Zander
to Marco van de Voort: Op 2019-07-04 om 17:36 schreef Michael Van Canneyt: If $ifdef was a single char token,…

Hi,

Marco van de Voort wrote 9 lines
> If $ifdef was a single char token, maybe. And for a trivial feature, not a core one, like conditional compiling. > > So the compiler will correctly give an error. ... but not at or near the place where the mistake is made.

Some languages uses multiple chars to mark start and end to solve that.  E.g. in XQuery there are strings with 3-char markers: |``[   ... |||]``||

Bye,
Benito

Reply by email

Tony
to Marco van de Voort: Op 2019-07-04 om 07:34 schreef Sven Barth via fpc-devel: Yes. And also that FPC changed…
Show quoted text 6 lines
In conclusion:  it is a solution in search of a problem, with bad behaviour in errorhandling (when unbalanced the compiler errors on perfectly fine code in the wrong place after whatever ' closes the unbalanced ) on top of it. This is why the feature goes against the grain of Pascal IMHO.

Well said Marco! I have been reading this mailing list for some time and have been disturbed recently-ish by how often suggestions come up for "my pet feature from another language" or "a cool idea I just had" (I am probably doing an injustice to some of the suggestions, but often they feel deeply un-Pascal-ish - I can't define it but I know it when I see it). In these circumstances, a healthy scepticism and conservatism among the development team is a good thing.

Tony

Reply by email

Sven Barth
to Benito van der Zander: Some languages uses multiple chars to mark start and end to solve that.  E.g. in XQuery…

Benito van der Zander schrieb am Fr., 5. Juli 2019, 11:33:

Show quoted text 19 lines
Hi, Am 04.07.19 um 19:51 schrieb Marco van de Voort: If $ifdef was a single char token, maybe. And for a trivial feature, not a core one, like conditional compiling. So the compiler will correctly give an error. ... but not at or near the place where the mistake is made. Some languages uses multiple chars to mark start and end to solve that. E.g. in XQuery there are strings with 3-char markers: ``[ ... ]``

And that would solve the problem if a missing termination how? It would be even worse, cause you could forget one of the backticks (e.g. on my systems it's a dead key, thus I also need to use space to get the character) and you might not easily see where it is missing.

Regards,
Sven

Reply by email

Ryan Joseph
to Ben Grasset: Ok, here's a link to my github fork <https://github.com/Akira13641/freepascal>…
On Jul 5, 2019, at 12:31 AM, Ben Grasset wrote: Ok, here's a link to my github fork implementing the multi-line string functionality.

Sweet. Why does the “cr” setting only print one line and “crlf” prints all of them? Sorry I wasn’t following along with all the talk.

It still feels intuitively like we should be using double-quotes instead of back ticks but it’s still very nice.

program test;
{$modeswitch multilinestrings}
{$multilinestringlineending cr}

const lines = `
aaa
bbb
ccc
ddd
`;

begin
  writeln(lines);
end.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph

On Fri, Jul 5, 2019 at 10:27 AM Ryan Joseph wrote

Sweet. Why does the “cr” setting only print one line and “crlf” prints all of them? Sorry I wasn’t following along with all the talk.

Not quite sure exactly what you mean.

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 5, 2019, at 10:40 AM, Ben Grasset wrote: Not quite sure exactly what you mean.

If use {$multilinestringlineending cr} then the string only prints “ ddd”. If I use {$multilinestringlineending crlf} then all the text prints.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
AM Ryan Joseph wrote
If use {$multilinestringlineending cr} then the string only prints “ ddd”. If I use {$multilinestringlineending crlf} then all the text prints.

Well, CR, (which is to say, #13) is extremely rarely used by itself (specifically it is native to only one FPC target, that being "classic" MacOS.)

Almost all other targets use LF (that is, #10) natively, besides Windows and a few others which use the *combination* of CR and LF natively.

What platform are you yourself on? Most likely, whatever software you were using to view the output (either a terminal, or a text editor after doing something like "./Example > output.txt") is simply not designed to recognize CR *by itself* as a valid line ending. Which is probably fine, as you would never use that setting unless targeting classic MacOS, or actually using classic MacOS.

Reply by email

Ben Grasset
to Tomas Hajny
AM Tomas Hajny wrote
That's what CR (Carriage Return) means, right? The cursor is moved to the beginning of the current line and writing continues there.

I believe he may have had CR mixed up with LF. (And by the sounds of it, his platform does specifically use LF as the native newline character.)

Reply by email

Ben Grasset
to Ryan Joseph: Sweet. Why does the “cr” setting only print one line and “crlf” prints all of…
AM Ryan Joseph wrote 16 lines
program test; {$modeswitch multilinestrings} {$multilinestringlineending cr} const lines = ` aaa bbb ccc ddd `; begin writeln(lines); end.

Also:

Just so nobody gets confused, if you want to test the feature, do not actually try to use the {$modeswitch multilinestrings}, as it does not exist *yet*.

Ryan's example in this case is what it *will* look like overall though, and it *does* compile as written, currently, if the line with the modeswitch is removed.

Reply by email

Ryan Joseph
to Ben Grasset

This may not be related but why does "l: string = lines;” work, shouldn’t that be an error or at least get clipped? I’m seeing writeln prints out the entire string as if it was an ansistring.

{$mode objfpc}
{$multilinestringlineending crlf}
{$h+}
program test;

const lines = `
#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;
  void main()
  {
    if (vertexUVMap == 255) {
      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;
var
  l: string = lines;
begin
  writeln(l);
end.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
AM Ryan Joseph wrote
This may not be related but why does "l: string = lines;” work, shouldn’t that be an error or at least get clipped? I’m seeing writeln prints out the entire string as if it was an ansistring.

Your example has nothing to do with multi-line strings specifically, and is completely normal, expected behavior when in {$H+}.

You could write the exact same constant string with single-line strings using the "addition operators and sLineBreak" method, and assign it to the variable the exact same way, and it would display identically.

Reply by email

Ben Grasset
to Ben Grasset
AM Ben Grasset wrote 14 lines
On Fri, Jul 5, 2019 at 11:29 AM Ryan Joseph wrote: > This may not be related but why does "l: string = lines;” work, shouldn’t > that be an error or at least get clipped? I’m seeing writeln prints out the > entire string as if it was an ansistring. > Your example has nothing to do with multi-line strings specifically, and is completely normal, expected behavior when in {$H+}. You could write the exact same constant string with single-line strings using the "addition operators and sLineBreak" method, and assign it to the variable the exact same way, and it would display identically.

Also, note that in all cases "untyped" constant strings behave exactly like ShortStrings or AnsiStrings, depending on whether {$H+} is being used, in every way (meaning, they can be passed *directly* to WriteLn with no intermediate variable required.) The only significant difference is that they are immutable, embedded-in-the-executable "true" constants.

Reply by email

Ben Grasset
to Ryan Joseph
AM Ryan Joseph wrote
So H+ makes all short strings ansistrings? I added that or I got an error about the string being too long.

It makes all "just String without the word Short or Ansi in front of it" variables AnsiStrings, and yes, enables "true constant" strings that are longer than 255 characters.

Explicit "ShortString" variables are still exactly what they say they are in all cases though, of course.

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 5, 2019, at 12:10 PM, Ben Grasset wrote: Explicit "ShortString" variables are still exactly what they say they are in all cases though, of course.

This may present a bit of problem then because you don't appear to be able to opt-in to long strings just for constants. $h+ will always be required for multi-line strings but I don’t want the rest of my “string” types to turn into ansistrings. Is there any solution to this?

// ERROR: String constant too long while ansistrings are disabled
{$h+}
const lines = `
  #version 150
  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;

void main()
{
if (vertexUVMap == 255) {

      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;

{$h-}

Regards,
Ryan Joseph

Reply by email

Sven Barth
to Ryan Joseph

Ryan Joseph schrieb am Fr., 5. Juli 2019, 19:14:

Show quoted text 13 lines
> On Jul 5, 2019, at 12:10 PM, Ben Grasset wrote: > > Explicit "ShortString" variables are still exactly what they say they are in all cases though, of course. > This may present a bit of problem then because you don't appear to be able to opt-in to long strings just for constants. $h+ will always be required for multi-line strings but I don’t want the rest of my “string” types to turn into ansistrings. Is there any solution to this?

Why should they always be required? If your multiline string is shorter than 256 characters then all is well.

And otherwise you'd have the same problem with an ordinary string constant.

So this behaves exactly as expected and desired.

You can also declare your string as a typed AnsiString constant in $H- mode:

lines: AnsiString = `lorem ipsum`;

Regards,
Sven

Reply by email

Ben Grasset
to Ryan Joseph: This may present a bit of problem then because you don't appear to be able to opt-in to…
PM Ryan Joseph wrote 5 lines
This may present a bit of problem then because you don't appear to be able to opt-in to long strings just for constants. $h+ will always be required for multi-line strings but I don’t want the rest of my “string” types to turn into ansistrings. Is there any solution to this?

I don't think it's really true that you'll *always* need long strings for multi-line stuff, however, if you're concerned about this in general there is in fact a way to switch between {$H+} and {$H-}:

program Example;
{$push}
{$H+}
var Ansi: String;
{$pop}
var Short: String;
begin
  WriteLn(GetTypeKind(Ansi));
  WriteLn(GetTypeKind(Short));
end.

which prints:

tkAString
tkSString

indicating they're the types you'd want / expect.

Reply by email

George Bakhtadze
to Sven Barth: In case case of readability: most cases of multi line string constants are likely to be…
In case case of readability: most cases of multi line string constants are likely to be embedded scripts (shaders, SQL, whatever) and thus the $INCLUDESTRING directive mentioned in the bug report is much more useable, because it allows you to view the embedded file in its own editor together with syntax hightlighting and possibly code completion.

Modern IDEs (e.g. IDEA) are able to inject language support into string literals allowing syntax highlighting, code completion and other code tools. Example:
http://siberika.com/img/db/inject.gif

Reply by email

Ryan Joseph
to Sven Barth: Ryan Joseph schrieb am Fr., 5. Juli 2019, 19:14: Why should they always be required? If…
Show quoted text 8 lines
On Jul 5, 2019, at 1:34 PM, Sven Barth via fpc-devel wrote: Why should they always be required? If your multiline string is shorter than 256 characters then all is well. And otherwise you'd have the same problem with an ordinary string constant. So this behaves exactly as expected and desired.

Sure, but I suspect majority of strings will be longer than 255. I guess this isn’t just multi-line string related but how do I declare a string constant that doesn’t then change “string” in the entire unit? I tried the typed constant but that doesn’t seem to work (got Illegal expression).

const lines: AnsiString = `
#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;
  void main()
  {
    if (vertexUVMap == 255) {
      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;

Regards,
Ryan Joseph

Reply by email

Ryan Joseph
to Ben Grasset: I don't think it's really true that you'll *always* need long strings for multi-line…
Show quoted text 6 lines
On Jul 5, 2019, at 1:36 PM, Ben Grasset wrote: {$push} {$H+} var Ansi: String; {$pop}

This doesn’t work either.

{$push}
{$h+}
var lines: ansistring = `
  #version 150
  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;

void main()
{
if (vertexUVMap == 255) {

      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;

{$pop}

Regards,
Ryan Joseph

Reply by email

Sven Barth
to Ryan Joseph: Sure, but I suspect majority of strings will be longer than 255. I guess this isn’t…
Ryan Joseph wrote 10 lines
> On Jul 5, 2019, at 1:34 PM, Sven Barth via fpc-devel wrote: > > Why should they always be required? If your multiline string is shorter than 256 characters then all is well. > > And otherwise you'd have the same problem with an ordinary string constant. > > So this behaves exactly as expected and desired. > Sure, but I suspect majority of strings will be longer than 255. I guess this isn’t just multi-line string related but how do I declare a string constant that doesn’t then change “string” in the entire unit? I tried the typed constant but that doesn’t seem to work (got Illegal expression).

I didn't get an Illegal Expression error (maybe that's still a problem of the multi line string support? I tested with a normal string), but the compiler nevertheless concatenates the string.

So in essence: if you want long string constants use $H+ mode.

Regards,
Sven

Reply by email

Sven Barth
to Ryan Joseph: This doesn’t work either. {$push} {$h+} var lines: ansistring = ` #version 150 uniform…
Ryan Joseph wrote 32 lines
> On Jul 5, 2019, at 1:36 PM, Ben Grasset wrote: > > {$push} > {$H+} > var Ansi: String; > {$pop} This doesn’t work either. {$push} {$h+} var lines: ansistring = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } }`; {$pop}

Works here if you use a good, old single line string. So it's probably some problem with the multiline string.

Regards,
Sven

Reply by email

Sven Barth
to Ben Grasset: I don't think it's really true that you'll *always* need long strings for multi-line…
Ben Grasset wrote 13 lines
On Fri, Jul 5, 2019 at 1:14 PM Ryan Joseph < > wrote: This may present a bit of problem then because you don't appear to be able to opt-in to long strings just for constants. $h+ will always be required for multi-line strings but I don’t want the rest of my “string” types to turn into ansistrings. Is there any solution to this? I don't think it's really true that you'll *always* need long strings for multi-line stuff, however, if you're concerned about this in general there is in fact a way to switch between {$H+} and {$H-}:

Right! I forgot that $H is a local directive, not a global one! 🤦‍♀️

Regards,
Sven

Reply by email

Ben Grasset
to Ryan Joseph: This doesn’t work either. {$push} {$h+} var lines: ansistring = ` #version 150 uniform…
PM Ryan Joseph wrote 29 lines
This doesn’t work either. {$push} {$h+} var lines: ansistring = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } }`; {$pop} Regards, Ryan Joseph

Doesn't work in what regard? You wouldn't even need {$H+} there, as you're explicitly using an ansistring.

Does something like the following not work for you:

program Example;

{$push}
{$H+}
const ReallyLongConstant = `
imagine
this
was
really
long
`;
{$pop}

var Short: String;
begin
  WriteLn(GetTypeKind(ReallyLongConstant));
  WriteLn(GetTypeKind(Short));
end.

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 5, 2019, at 4:30 PM, Ben Grasset wrote: Doesn't work in what regard? You wouldn't even need {$H+} there, as you're explicitly using an ansistring.

The problem is I was using ObjFPC mode. Works fine in Delphi. A bug?

{$mode objfpc}
{$modeswitch multilinestrings}
{$multilinestringlineending crlf}
program test;
{$push}
{$H+}
const lines = `
  #version 150
  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;

void main()
{
if (vertexUVMap == 255) {

      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;

{$pop}

begin
  writeln(lines);
end.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
PM Ryan Joseph wrote 36 lines
The problem is I was using ObjFPC mode. Works fine in Delphi. A bug? {$mode objfpc} {$modeswitch multilinestrings} {$multilinestringlineending crlf} program test; {$push} {$H+} const lines = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } }`; {$pop} begin writeln(lines); end.

I'll have to look at this later today when I have more free time. I did however test a variety of things (both typed and untyped constants and variables, and also literals in function calls, and had no issues.)

Note again that {$modeswitch multilinestrings} does not exist yet, though. Try putting your directives after "program", not before, also.

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 5, 2019, at 4:39 PM, Ben Grasset wrote: I'll have to look at this later today when I have more free time. I did however test a variety of things (both typed and untyped constants and variables, and also literals in function calls, and had no issues.)

Thanks. I don’t even need H+ in delphi mode so maybe it’s enabled by default. In ObjFPC mode H+ doesn’t seem to be working unless it’s before the program section.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ben Grasset: I'll have to look at this later today when I have more free time. I did however test a…
PM Ben Grasset wrote 7 lines
I'll have to look at this later today when I have more free time. I did however test a variety of things (both typed and untyped constants and variables, and also literals in function calls, and had no issues.) Note again that {$modeswitch multilinestrings} does not exist yet, though. Try putting your directives after "program", not before, also.

Also, in general, my implementation as it stands is entirely unrelated to any part of the compiler that cares about the overall "langauge modes". It is implemented entirely in the scanner, and simply builds upon the existing string-reading code.

Even the in-progress {$modeswitch} isn't really going to be heavily concerned with anything other than whether it specifically is on or off, because it doesn't need to be.

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 5, 2019, at 5:45 PM, Ben Grasset wrote: Like, not working in any sense at all? That's definitely not normal.

I think it’s just the push/pop isn’t working. Just to be clear should the follow code compile? For me I get an error.Try it yourself when you get some time.

{$mode objfpc}
program test;
{$push}
{$H+}
const lines = `
  #version 150
  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;

void main()
{
if (vertexUVMap == 255) {

      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;

{$pop}

begin
  writeln(lines);
end.

Regards,
Ryan Joseph

Reply by email

Sven Barth
to Ben Grasset: Doesn't work in what regard? You wouldn't even need {$H+} there, as you're explicitly…
Ben Grasset wrote 38 lines
On Fri, Jul 5, 2019 at 1:41 PM Ryan Joseph < > wrote: This doesn’t work either. {$push} {$h+} var lines: ansistring = `   #version 150   uniform sampler2D textures[8];   in vec2 vertexTexCoord;   in vec4 vertexColor;   in float vertexUVMap;   out vec4 fragColor;   void main()   {     if (vertexUVMap == 255) {       fragColor = vertexColor;     } else {       fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);       if (vertexColor.a < fragColor.a) {         fragColor.a = vertexColor.a;       }     }   }`; {$pop} Regards,         Ryan Joseph Doesn't work in what regard? You wouldn't even need {$H+} there, as you're explicitly using an ansistring.

The constant itself is parsed depending on the state of $H and only then "assigned" to the constant (just tested that myself). So the directives are needed to get the correct string type of the constant.

Regards,
Sven

Reply by email

Sven Barth
to Ryan Joseph: I think it’s just the push/pop isn’t working. Just to be clear should the follow code…
Ryan Joseph wrote 38 lines
> On Jul 5, 2019, at 5:45 PM, Ben Grasset wrote: > > Like, not working in any sense at all? That's definitely not normal. > I think it’s just the push/pop isn’t working. Just to be clear should the follow code compile? For me I get an error.Try it yourself when you get some time. {$mode objfpc} program test; {$push} {$H+} const lines = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } }`; {$pop} begin writeln(lines); end.

Ah! Check the location of the error. It's the Writeln, not the declaration of the constant. Seems like the compiler doesn't correctly handle this case. But to be fair it's really seldom that someone uses $H locally, so that's not really a tested situation...

Regards,
Sven

Reply by email

Ben Grasset
to Sven Barth: The constant itself is parsed depending on the state of $H and only then "assigned" to…

On Fri, Jul 5, 2019 at 6:41 PM Sven Barth via fpc-devel <

Show quoted text 6 lines
wrote: The constant itself is parsed depending on the state of $H and only then "assigned" to the constant (just tested that myself). So the directives are needed to get the correct string type of the constant
{$H+} is definitely not needed for an explicit 'var string: ansistring'. It
works even with {$H-}.

After looking at Ryan's more complete example though, the use of {$mode SomeLanguageMode} *before* pushing {$H+} does seem to make {$H+} not recognized. I do not believe that this behaviour is related to any code I've added so far, however, as I don't see how it possibly could be. Seems like a bug that nobody came across before.

That said, writing the following *does* work:

program test;
{$push}
{$mode objfpc}
{$H+}

const lines = `
#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;

void main()
{
if (vertexUVMap == 255) {

      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;

{$pop}

begin
  writeln(lines);
end.

I'm still very unclear about where Ryan said he got "illegal expression" and such, though. I just now tested another large number of possible ways you can use multi-line strings, and they all do work.

On Fri, Jul 5, 2019 at 6:41 PM Sven Barth via fpc-devel <

Show quoted text 51 lines
wrote: Am 05.07.2019 um 22:30 schrieb Ben Grasset: On Fri, Jul 5, 2019 at 1:41 PM Ryan Joseph wrote: > This doesn’t work either. > > {$push} > {$h+} > var lines: ansistring = ` > #version 150 > > uniform sampler2D textures[8]; > in vec2 vertexTexCoord; > in vec4 vertexColor; > in float vertexUVMap; > out vec4 fragColor; > > void main() > { > if (vertexUVMap == 255) { > fragColor = vertexColor; > } else { > fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); > if (vertexColor.a < fragColor.a) { > fragColor.a = vertexColor.a; > } > } > }`; > {$pop} > > Regards, > Ryan Joseph > Doesn't work in what regard? You wouldn't even need {$H+} there, as you're explicitly using an ansistring. The constant itself is parsed depending on the state of $H and only then "assigned" to the constant (just tested that myself). So the directives are needed to get the correct string type of the constant. Regards, Sven _______________________________________________ fpc-devel maillist - https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-devel

Reply by email

Ben Grasset
to Ben Grasset
PM Ben Grasset wrote
I'm still very unclear about where Ryan said he got "illegal expression" and such, though. I just now tested another large number of possible ways you can use multi-line strings, and they all do work.

As an (extreme) example of something that *does*, and should, work:

program BadFormatting;
         begin

writeln (`a

b
c
d
e
f`

);
   end.

Reply by email

Ryan Joseph
to Ben Grasset: On Fri, Jul 5, 2019 at 6:41 PM Sven Barth via fpc-devel < {$H+} is definitely not needed…
On Jul 5, 2019, at 7:33 PM, Ben Grasset wrote: {$H+} is definitely not needed for an explicit 'var string: ansistring'. It works even with {$H-}.

Do you mean this? I still get an error without H+.

{$mode objfpc}
program test;

var lines: ansistring = `
#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;
  void main()
  {
    if (vertexUVMap == 255) {
      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;
After looking at Ryan's more complete example though, the use of {$mode SomeLanguageMode} *before* pushing {$H+} does seem to make {$H+} not recognized. I do not believe that this behaviour is related to any code I've added so far, however, as I don't see how it possibly could be. Seems like a bug that nobody came across before.

Then it’s a bug I guess? That would be nice to fix because it will be a problem for exiting code if we’re forced to turn on H+ for the entire unit. It’s probably not related to your code I agree. If anyone know if this is a bug/can be fixed please let me know.

Regards,
Ryan Joseph

Reply by email

Ryan Joseph
to Sven Barth: Ah! Check the location of the error. It's the Writeln, not the declaration of the…
On Jul 5, 2019, at 6:48 PM, Sven Barth via fpc-devel wrote: Ah! Check the location of the error. It's the Writeln, not the declaration of the constant. Seems like the compiler doesn't correctly handle this case. But to be fair it's really seldom that someone uses $H locally, so that's not really a tested situation...

I’m confused now. The error is coming from the middle of the string after it exceeds the character limit. Can we fix this? If it’s possible to turn on longer than 255 char multiline strings locally that’s going to be a problem for existing code because H+ is global for the unit it appears.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph: Do you mean this? I still get an error without H+. {$mode objfpc} program test; var…
PM Ryan Joseph wrote 27 lines
Do you mean this? I still get an error without H+. {$mode objfpc} program test; var lines: ansistring = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } }`;

Copy and paste this exact code into a file called test.pas:

{$mode objfpc}
{ explicitly set H- ! }
{$H-}
program test;

var lines: ansistring = `
#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;
  void main()
  {
    if (vertexUVMap == 255) {
      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;
begin
  WriteLn(lines);
end.

With a build of my fork of the compiler as uploaded, compiling it with simply "fpc ./test.pas" works without issues, and it runs like you'd expect.

If that somehow is not the case for you, what is the *exact* error you're getting?

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 5, 2019, at 8:04 PM, Ben Grasset wrote: With a build of my fork of the compiler as uploaded, compiling it with simply "fpc ./test.pas" works without issues, and it runs like you'd expect.

ah! Your code works but mine doesn’t! maybe the line ending are messing it up? I get "String constant too long while ansistrings are disabled”.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph: I’m confused now. The error is coming from the middle of the string after it exceeds…
PM Ryan Joseph wrote 5 lines
I’m confused now. The error is coming from the middle of the string after it exceeds the character limit. Can we fix this? If it’s possible to turn on longer than 255 char multiline strings locally that’s going to be a problem for existing code because H+ is global for the unit it appears.

To be clear: multiline strings are *just* strings in every way. I have not introduced *anything* remotely resembling a new type. It is literally just a matter of the compiler not stopping at newline characters, and instead continuing to read until it hits a backtick. Pure, incredibly simplistic scanner functionality.

Pushing and popping {$H+} *does* also work in general, but indeed seems to be affected in some way by {$mode}. This should probably be fixed, but it's unrelated to the patch we're discussing here, and not something I'm particularly concerned about at the moment.

Reply by email

Ben Grasset
to Ryan Joseph: ah! Your code works but mine doesn’t! maybe the line ending are messing it up? I get…
PM Ryan Joseph wrote
ah! Your code works but mine doesn’t! maybe the line ending are messing it up? I get "String constant too long while ansistrings are disabled”.\

No, that makes no sense whatsoever.

Another example:

{$mode objfpc}
{ explicitly set H- ! }
{$H-}
{ using CRLF while my file is actually LF, just for fun }
{$MULTILINESTRINGLINEENDING CRLF}
program test;

var lines: ansistring = `
#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;
  void main()
  {
    if (vertexUVMap == 255) {
      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
  }`;
begin
  WriteLn(lines);
end.

I'm not even sure which code (that is actually a complete program with a begin and end) you're talking about.

Reply by email

Ben Grasset
to Ben Grasset
PM Ben Grasset wrote 46 lines
On Fri, Jul 5, 2019 at 8:08 PM Ryan Joseph wrote: > ah! Your code works but mine doesn’t! maybe the line ending are messing > it up? I get "String constant too long while ansistrings are disabled”.\ > No, that makes no sense whatsoever. Another example: {$mode objfpc} { explicitly set H- ! } {$H-} { using CRLF while my file is actually LF, just for fun } {$MULTILINESTRINGLINEENDING CRLF} program test; var lines: ansistring = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } }`; begin WriteLn(lines); end. I'm not even sure which code (that is actually a complete program with a begin and end) you're talking about.
I just noticed, in fact: the compiler actually completely ignores {$H+} and
{$H-} for "typed" string constants *and* variables, in all cases. Even with
{$H-}, and with not "ansistring", but "string", my above example still
works (i.e. the compiler implicitly "uptypes" it to an ansistring if it
needs to, basically). Only for "true constant" strings does it care about
{$H+} and 'm unsure whether or not this is intentional behaviour.

Reply by email

Ben Grasset
to Ryan Joseph
PM Ryan Joseph wrote
I just tried pasting some code from Sublime Text into the string and I get the error. If I copy your code or just type myself the error goes away. I’m on a Mac btw so it may have something to do with that.

What error, though?

Reply by email

Ben Grasset
to Ryan Joseph
PM Ryan Joseph wrote 5 lines
String constant too long while ansistrings are disabled Regards, Ryan Joseph

Getting that with "var SomeString: AnsiString = " should be (and is) impossible at all times.

Getting that with "var SomeString: String = " only *maybe* should be (but is regardless) impossible at all times.

Getting that with "const SomeString = " when in {$H-} is expected at all times.

Getting that with "const SomeString = " when in {$H+} should be (and is) impossible at all times.

Typed constants / variables and untyped constants are *not* the same thing.

Reply by email

J. Gareth Moreton
to Ben Grasset

If someone has reported it, then it's not impossible.  Granted, a reproducible case helps here, along with any configuration settings.

Gareth aka. Kit

Ben Grasset wrote 27 lines
On Fri, Jul 5, 2019 at 10:37 PM Ryan Joseph < > wrote: String constant too long while ansistrings are disabled Regards,         Ryan Joseph Getting that with "var SomeString: AnsiString = " should be (and is) impossible at all times. Getting that with "var SomeString: String = "  only *maybe* should be (but is regardless) impossible at all times. Getting that with "const SomeString = " when in {$H-} is expected at all times. Getting that with "const SomeString = " when in {$H+} should be (and is) impossible at all times. Typed constants / variables and untyped constants are *not* the same thing. _______________________________________________ fpc-devel maillist - https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-devel

---
This email has been checked for viruses by Avast antivirus software. https://www.avast.com/antivirus

Reply by email

Ben Grasset

Ok, I've implemented {$modeswitch MultiLineStrings}.

The compiler now stops immediately with "file.pas(lineno,lineno) Fatal: Illegal character "'`'" ($60)" (which I find to be more informative than "illegal expression") upon any occurrence of a backtick outside a single-line string when the modeswitch is disabled (which it is by default in all "language modes", currently.)

If desired, I can make it on-by-default in *some* specific mode (or modes). Or not. Doesn't really matter to me personally.

Again, if anyone wants to test the branch, my github can be found here. <https://github.com/Akira13641/freepascal>

I'm now going to start working on writing a suite of FPC-test-suite compatible tests, I guess.

Reply by email

Ben Grasset
to J. Gareth Moreton: If someone has reported it, then it's not impossible.  Granted, a reproducible case…
PM J. Gareth Moreton wrote
If someone has reported it, then it's not impossible. Granted, a reproducible case helps here, along with any configuration settings.

He hasn't reported anything, so far, that isn't just how strings have always worked. The only real issue we've uncovered is the strange behavior of {$mode} as it relates to {$push} and {$pop}.

Reply by email

Tomas Hajny
to Ben Grasset

On 2019-07-06 05:06, Ben Grasset wrote:

.
.

Show quoted text 5 lines
He hasn't reported anything, so far, that isn't just how strings have always worked. The only real issue we've uncovered is the strange behavior of {$mode} as it relates to {$push} and {$pop}.

Have you tested command-line compilation with a CR-only source file? Since this is what he mentioned to be using (because being on a Mac)... There may be some difference on the scanner side in theory...

Tomas

Reply by email

Ben Grasset
to Tomas Hajny
AM Tomas Hajny wrote
Have you tested command-line compilation with a CR-only source file? Since this is what he mentioned to be using (because being on a Mac)... There may be some difference on the scanner side in theory...

I have. It works fine, because of course it does.

Everything he was talking about was clearly based on fundamentally not understanding the basic differences between things like "const SomeString: String = " and "var SomeString: AnsiString = ", and assuming that they were somehow *supposed* to be affected the same way by {$H+}, and so on.

Sorry for getting a bit frustrated everyone, but it's annoying to have this long back and forth discussion about a vague "problem" that simply does not exist.

Reply by email

Ben Grasset
to Ben Grasset
AM Ben Grasset wrote 9 lines
On Sat, Jul 6, 2019 at 1:34 AM Tomas Hajny wrote: > Have you tested command-line compilation with a CR-only source file? > Since this is what he mentioned to be using (because being on a Mac)... > There may be some difference on the scanner side in theory... -snip- "const SomeString: String = " -snip-

I meant that to be "const SomeString ="

AM Ben Grasset wrote 22 lines
On Sat, Jul 6, 2019 at 1:34 AM Tomas Hajny wrote: > Have you tested command-line compilation with a CR-only source file? > Since this is what he mentioned to be using (because being on a Mac)... > There may be some difference on the scanner side in theory... > I have. It works fine, because of course it does. Everything he was talking about was clearly based on fundamentally not understanding the basic differences between things like "const SomeString: String = " and "var SomeString: AnsiString = ", and assuming that they were somehow *supposed* to be affected the same way by {$H+}, and so on. Sorry for getting a bit frustrated everyone, but it's annoying to have this long back and forth discussion about a vague "problem" that simply does not exist.

Reply by email

Ben Grasset

General question regarding the tests I'm writing:

What kind of numbers should I be going for? Is something like 10 that pass and 10 that fail a good ratio? Or should it be more of them that pass?

Also, is using the names "tmultilinestrings1.pp", "tmultilinestrings2.pp", e.t.c. appropriate?

Reply by email

Ryan Joseph
to Ben Grasset: I have. It works fine, because of course it does. Everything he was talking about was…
Show quoted text 6 lines
On Jul 6, 2019, at 8:07 AM, Ben Grasset wrote: Everything he was talking about was clearly based on fundamentally not understanding the basic differences between things like "const SomeString: String = " and "var SomeString: AnsiString = ", and assuming that they were somehow *supposed* to be affected the same way by {$H+}, and so on. Sorry for getting a bit frustrated everyone, but it's annoying to have this long back and forth discussion about a vague "problem" that simply does not exist.

I got it now, using typed constants is the solution. I got confused with $H+ stuff and probably just wasn’t paying enough attention.

Btw, here is the "Illegal expression” error which I mentioned before but lost track of.

==========

{$mode objfpc}
program test;

const lines: ansistring = `
#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;
  void main()
  {
    if (vertexUVMap == 255) {
      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
    // TODO: testing
    fragColor = vec4(1,0,0,1);
  }
`;
var
  s: ansistring = lines;
begin
  writeln(lines);
end.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
AM Ryan Joseph wrote 43 lines
Btw, here is the "Illegal expression” error which I mentioned before but lost track of. ========== {$mode objfpc} program test; const lines: ansistring = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } // TODO: testing fragColor = vec4(1,0,0,1); } `; var s: ansistring = lines; begin writeln(lines); end. Regards, Ryan Joseph

That really is an illegal expression (I.E. once again expected behavior) whether multi-line strings are involved or not. The following is equally invalid:

{$mode objfpc}
program test;
const lines: ansistring = 'just a single line string';
var
  s: ansistring = lines;
begin
  writeln(lines);
end.

You cannot under any circumstances initialize a variable with a "typed" constant, because typed constants are themselves mutable by default.

Reply by email

Ben Grasset
to Tony: On Thu, 4 Jul 2019 12:00:07 +0200 Well said Marco! I have been reading this mailing list…

On Sat, Jul 6, 2019 at 2:15 AM Tony via fpc-devel <

Show quoted text 20 lines
wrote: On Thu, 4 Jul 2019 12:00:07 +0200 Marco van de Voort wrote: > In conclusion: it is a solution in search of a problem, with bad > behaviour in errorhandling (when unbalanced the compiler errors on > perfectly fine code in the wrong place after whatever ' closes the > unbalanced ) on top of it. > > This is why the feature goes against the grain of Pascal IMHO. Well said Marco! I have been reading this mailing list for some time and have been disturbed recently-ish by how often suggestions come up for "my pet feature from another language" or "a cool idea I just had" (I am probably doing an injustice to some of the suggestions, but often they feel deeply un-Pascal-ish - I can't define it but I know it when I see it). In these circumstances, a healthy scepticism and conservatism among the development team is a good thing.

I think you are certainly doing injustice to a lot of things. Furthermore, you realize it is possible, to just, you know, make the compiler give better errors when necessary / desired?

I intend to add something like this for unterminated multi-line strings, most likely once I'm done writing my tests and have submitted a formal patch on the bugtracker.

Reply by email

Ryan Joseph
to Ben Grasset: That really is an illegal expression (I.E. once again expected behavior) whether…
On Jul 6, 2019, at 9:56 AM, Ben Grasset wrote: You cannot under any circumstances initialize a variable with a "typed" constant, because typed constants are themselves mutable by default.

Ok so typed constants are not really constants. Makes sense. :) The error also doesn’t make any sense. To the compiler team, could we make that error actually tell us what’s wrong?

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
AM Ryan Joseph wrote 8 lines
> On Jul 6, 2019, at 9:56 AM, Ben Grasset wrote: > > You cannot under any circumstances initialize a variable with a "typed" constant, because typed constants are themselves mutable by default. > Ok so typed constants are not really constants. Makes sense. :)

Well, it's Borland who is to blame for this, specifically.

FPC has the behaviour because it needs to for the sake of compatibility. Certainly though, I've always wished that only initialized *variables*, using "var Something: Type = " as opposed to "const Something: Type = " existed, and that all consts were specifically untyped like "const Something = ".

Sadly that is not and will never be the case, unfortunately.

Reply by email

Florian Klämpfl
to Ryan Joseph: This may not be related but why does "l: string = lines;” work, shouldn’t that be an…
Ryan Joseph wrote 28 lines
This may not be related but why does "l: string = lines;” work, shouldn’t that be an error or at least get clipped? I’m seeing writeln prints out the entire string as if it was an ansistring. {$mode objfpc} {$multilinestringlineending crlf} {$h+} program test; const lines = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } }`;

I tried to follow the thread, but one think I miss is: what are the rules for indention? Does the lines string contain spaces at the beginning of every line or not? Are they removed? How many are removed? What about tabs? Actually, this is my main concern with such multiline strings: spaces/tabs at the beginning of a line cannot be handled in an intuitive way.

Reply by email

Ben Grasset
to Florian Klämpfl
AM Florian Klämpfl wrote 7 lines
I tried to follow the thread, but one think I miss is: what are the rules for indention? Does the lines string contain spaces at the beginning of every line or not? Are they removed? How many are removed? What about tabs? Actually, this is my main concern with such multiline strings: spaces/tabs at the beginning of a line cannot be handled in an intuitive way.

No spaces or tabs are implicitly inserted or removed by the compiler at any time. Line endings are handled via the directive syntax suggested by Michael.

If you wish to test the feature yourself, Florian, currently I have the branch available here. <https://github.com/Akira13641/freepascal>

Note that it *does* now also include the requested {$modeswitch MultiLineStrings}, which must be set (in all language modes) in order to use multi-line strings anywhere.

Reply by email

Ben Grasset
to Ben Grasset
AM Ben Grasset wrote 11 lines
No spaces or tabs are implicitly inserted or removed by the compiler at any time. Line endings are handled via the directive syntax suggested by Michael. If you wish to test the feature yourself, Florian, currently I have the branch available here. <https://github.com/Akira13641/freepascal> Note that it *does* now also include the requested {$modeswitch MultiLineStrings}, which must be set (in all language modes) in order to use multi-line strings anywhere.

To be extra clear, also, for example, in the case of that code posted by Ryan the output looks like this:

#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;
  void main()
  {
    if (vertexUVMap == 255) {
      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
    // TODO: testing
    fragColor = vec4(1,0,0,1);
  }

Which is to say, two spaces are present at the start of each line because they were present in the string as Ryan typed it.

AM Ben Grasset wrote 22 lines
On Sat, Jul 6, 2019 at 10:25 AM Florian Klämpfl wrote: > I tried to follow the thread, but one think I miss is: what are the rules > for indention? Does the lines string contain > spaces at the beginning of every line or not? Are they removed? How many > are removed? What about tabs? Actually, this is > my main concern with such multiline strings: spaces/tabs at the beginning > of a line cannot be handled in an intuitive way. > No spaces or tabs are implicitly inserted or removed by the compiler at any time. Line endings are handled via the directive syntax suggested by Michael. If you wish to test the feature yourself, Florian, currently I have the branch available here. <https://github.com/Akira13641/freepascal> Note that it *does* now also include the requested {$modeswitch MultiLineStrings}, which must be set (in all language modes) in order to use multi-line strings anywhere.

Reply by email

Ryan Joseph
to Ben Grasset: Well, it's Borland who is to blame for this, specifically. FPC has the behaviour because…

Ben, I think that the multiline strings are messing up the current file info so errors are appearing at the wrong place. The “illegal expression” should appear at the variable initialization but it’s appearing in the middle of the string instead. If you remove any new lines from the string you’ll see the error gets moved to the right location.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
AM Ryan Joseph wrote 7 lines
Ben, I think that the multiline strings are messing up the current file info so errors are appearing at the wrong place. The “illegal expression” should appear at the variable initialization but it’s appearing in the middle of the string instead. If you remove any new lines from the string you’ll see the error gets moved to the right location.

I'll have to look at exactly how the errors get propagated in that scenario. None of my code directly involves the "file info", though.

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 6, 2019, at 10:50 AM, Ben Grasset wrote: I'll have to look at exactly how the errors get propagated in that scenario. None of my code directly involves the "file info", though.

Try this test. I get Identifier not found “b” at 18:11.

=====================

{$mode objfpc}
program test;

const lines: ansistring = `
#version 150

  uniform sampler2D textures[8];
  in vec2 vertexTexCoord;
  in vec4 vertexColor;
  in float vertexUVMap;
  out vec4 fragColor;
  void main()
  {
    if (vertexUVMap == 255) {
      fragColor = vertexColor;
    } else {
      fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st);
      if (vertexColor.a < fragColor.a) {
        fragColor.a = vertexColor.a;
      }
    }
    // TODO: testing
    fragColor = vec4(1,0,0,1);
  }
`;
var
  s: ansistring;
begin
  writeln(b);
end.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
AM Ryan Joseph wrote 38 lines
{$mode objfpc} program test; const lines: ansistring = ` #version 150 uniform sampler2D textures[8]; in vec2 vertexTexCoord; in vec4 vertexColor; in float vertexUVMap; out vec4 fragColor; void main() { if (vertexUVMap == 255) { fragColor = vertexColor; } else { fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); if (vertexColor.a < fragColor.a) { fragColor.a = vertexColor.a; } } // TODO: testing fragColor = vec4(1,0,0,1); } `; var s: ansistring; begin writeln(b); end. Regards, Ryan Joseph

Yep. I was actually just writing a couple of tests that directly look at how errors are handled, so this might prove as a good case for one of them once I get it remedied.

Reply by email

Ben Grasset
to Ben Grasset
AM Ben Grasset wrote
Yep. I was actually just writing a couple of tests that directly look at how errors are handled, so this might prove as a good case for one of them once I get it remedied.

Ok, I see exactly what's wrong (or more specifically, missing) in my modified "scanner.pas", actually. Won't be hard to fix.

Reply by email

Sven Barth
to Florian Klämpfl: I tried to follow the thread, but one think I miss is: what are the rules for indention?…
Florian Klämpfl wrote 32 lines
Am 05.07.2019 um 17:29 schrieb Ryan Joseph: > This may not be related but why does "l: string = lines;” work, shouldn’t that be an error or at least get clipped? I’m seeing writeln prints out the entire string as if it was an ansistring. > > {$mode objfpc} > {$multilinestringlineending crlf} > {$h+} > > program test; > > const lines = ` > #version 150 > > uniform sampler2D textures[8]; > in vec2 vertexTexCoord; > in vec4 vertexColor; > in float vertexUVMap; > out vec4 fragColor; > > void main() > { > if (vertexUVMap == 255) { > fragColor = vertexColor; > } else { > fragColor = texture(textures[int(vertexUVMap)], vertexTexCoord.st); > if (vertexColor.a < fragColor.a) { > fragColor.a = vertexColor.a; > } > } > }`; I tried to follow the thread, but one think I miss is: what are the rules for indention? Does the lines string contain spaces at the beginning of every line or not? Are they removed? How many are removed? What about tabs? Actually, this is my main concern with such multiline strings: spaces/tabs at the beginning of a line cannot be handled in an intuitive way.

I've also complained about that point here:
https://lists.freepascal.org/pipermail/fpc-devel/2019-July/041453.html

Regards,
Sven

Reply by email

Sven Barth
to Ben Grasset: General question regarding the tests I'm writing: What kind of numbers should I be going…
Ben Grasset wrote 5 lines
General question regarding the tests I'm writing: What kind of numbers should I be going for? Is something like 10 that pass and 10 that fail a good ratio? Or should it be more of them that pass?

It's not about the ratio of passing and failing tests or a general number of tests. You should simply try to cover as many cases as possible to ensure that
A) the feature works as intended
B) things that shouldn't work indeed don't work

Also, is using the names "tmultilinestrings1.pp", "tmultilinestrings2.pp", e.t.c. appropriate?

Yes. Though you can use the singular as well.

Regards,
Sven

Reply by email

Ryan Joseph
to Sven Barth: I've also complained about that point here: https://lists.freepascal.org/pipermail/fpc-dev…
On Jul 6, 2019, at 11:38 AM, Sven Barth via fpc-devel wrote: I've also complained about that point here: https://lists.freepascal.org/pipermail/fpc-devel/2019-July/041453.html

For your case:

const SomeString = `Whatever
bar
blubb

                    foobar`;

Is it better to add a feature in to the compiler or just do some post processing on the string using a function? You can of course shift the strings all the way to the left (which is ugly), do a post processing function (to keep it pretty), or just not use them at all and go back to what ever you were doing before. Either way we get more options available to us so this feature is a big win imo.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
AM Ryan Joseph wrote
You can of course shift the strings all the way to the left (which is ugly)

Is it though? I think it looks fine, personally, if you place the initial backtick on the next line after the equal sign, like this:

const MultiLine =
`Sentence one.
Another sentence.
A third sentence.
A fourth sentence.
A fifth sentence.`;

Do keep in mind that I also have working syntax highlighting for this that I intend to submit as a Lazarus SynEdit patch, which includes the ability to "fold" a multi-line string as though it were a multi-line comment. Of course, not everyone uses Lazarus, but many many people do.

In general though I think that using indentation as an actual "argument" against this is very strange (which I know you were not doing, to be clear.)

The *most* logical way for it to work (and how it does work currently) is for the strings to be interpreted by the compiler precisely as they are written (with the exception of the line endings, which are of course handled with Michael's directive syntax.)

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 6, 2019, at 12:05 PM, Ben Grasset wrote: Is it though? I think it looks fine, personally, if you place the initial backtick on the next line after the equal sign, like this:

It’s ugly imo, but that doesn’t matter because it’s better than nothing AND we can do a post processing if the user wants to indent but remove the white space later. Just make a RemoveLeadingWhiteSpace function or something and add it to the RTL.

Regards,
Ryan Joseph

Reply by email

Ryan Joseph
to Ryan Joseph

Just thought of something. Why would it be a bad idea to have a switch like H+ that makes all single quoted strings become multiline? I can’t think of a reason off the top of my head which would mess up any of my programs if suddenly strings were allowed to be more than one line.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
PM Ryan Joseph wrote 5 lines
Just thought of something. Why would it be a bad idea to have a switch like H+ that makes all single quoted strings become multiline? I can’t think of a reason off the top of my head which would mess up any of my programs if suddenly strings were allowed to be more than one line.

Notwithstanding the fact that I'm 100% certain that would never be accepted, given the relative level of controversy that exists even over my implementation as it exists, I just don't think that's really worth it. The backtick does not make it any more unwieldy IMO as it is still just one character.

Also, I'm not sure that could be implemented without introducing way too many checks that would ultimately have at least a minorly noticeable impact of compiler performance.

The backtick way allows the implementation to stay relatively straightforward and lightweight.

Reply by email

Florian Klaempfl
to Sven Barth: I've also complained about that point here: https://lists.freepascal.org/pipermail/fpc-dev…
Sven Barth wrote 9 lines
> I tried to follow the thread, but one think I miss is: what are the > rules for indention? Does the lines string contain > spaces at the beginning of every line or not? Are they removed? How > many are removed? What about tabs? Actually, this is > my main concern with such multiline strings: spaces/tabs at the > beginning of a line cannot be handled in an intuitive way. I've also complained about that point here: https://lists.freepascal.org/pipermail/fpc-devel/2019-July/041453.html

Sorry, I missed this one ;(

Reply by email

Ben Grasset

I've now corrected the error-message positioning oversight that Ryan pointed out and committed the change to my fork-branch, for anyone following along.

Once again I'll note also, for anyone updating or pulling the fork for the first time:

{$modeswitch MultiLineStrings} *does* exist now, and you will get a
compiler error if you don't use it.

Reply by email

Unknown author
to Ben Grasset: Is it though? I think it looks fine, personally, if you place the initial backtick on the…
Ben Grasset wrote 13 lines
On Sat, Jul 6, 2019 at 11:51 AM Ryan Joseph wrote: You can of course shift the strings all the way to the left (which is ugly) Is it though? I think it looks fine, personally, if you place the initial backtick on the next line after the equal sign, like this: const MultiLine = `Sentence one. Another sentence. A third sentence. A fourth sentence. A fifth sentence.`;

procedure foo
procedure bar
const MultiLine1 =
`Sentence one.
Another sentence.
A third sentence.
A fourth sentence.

            A fifth sentence.`;
           MultiLine2 = `Sentence one.
                         Another sentence.
                         A third sentence.
                         A fourth sentence.
                         A fifth sentence.`;
           MultiLine3 = `Sentence one.

Another sentence.
A third sentence.
A fourth sentence.
A fifth sentence.`;

     begin
       writeln("MultiLine1= '",MultiLine1,"'");
       writeln("MultiLine2= '",MultiLine2,"'");
     end;
   begin
     bar;
   end;

end;

?

just asking... can't test... the private procedure is specifically to exhibit various formats and to query what the output would be... intended output in this case is

'Sentence one.
Another sentence.
A third sentence.
A fourth sentence.
A fifth sentence.

In general though I think that using indentation as an actual "argument" against this is very strange (which I know you were not doing, to be clear.)

one person's PrettyPrint format is another's ugly-as-sin ;)

NOTE: No off-list assistance is given without prior approval. *Please keep mailing list traffic on the list unless* *a signed and pre-paid contract is in effect with us.*

Reply by email

Ben Grasset
to Unknown author
PM wrote 6 lines
just asking... can't test... the private procedure is specifically to exhibit various formats and to query what the output would be... intended output in this case is

The output is always exactly what is written (apart from the line endings.)

You cannot, in my opinion at least, reasonably expect something like this to *ignore* all indentation and still function in any logical way. That the leading whitespace is taken at "face value" is a large part of what makes it useful for anything at all.

Reply by email

Ben Grasset
to Ben Grasset
PM Ben Grasset wrote 5 lines
You cannot, in my opinion at least, reasonably expect something like this to *ignore* all indentation and still function in any logical way. That the leading whitespace is taken at "face value" is a large part of what makes it useful for anything at all.

That said: it may, eventually, be possible for me to add an additional directive taking a number that indicates how many spaces to *remove* from the beginning of a line (but never add.)

At the moment I'm more concerned with getting my tests written and making sure the feature overall works properly and doesn't break anything though, so don't expect this as an out-of-the-box additional aspect of it or anything like that.

Reply by email

Sven Barth
to Florian Klaempfl: Sorry, I missed this one ;(

Florian Klaempfl schrieb am Sa., 6. Juli 2019,
21:18:

Show quoted text 13 lines
Am 06.07.2019 um 17:38 schrieb Sven Barth via fpc-devel: >> I tried to follow the thread, but one think I miss is: what are the >> rules for indention? Does the lines string contain >> spaces at the beginning of every line or not? Are they removed? How >> many are removed? What about tabs? Actually, this is >> my main concern with such multiline strings: spaces/tabs at the >> beginning of a line cannot be handled in an intuitive way. > I've also complained about that point here: > https://lists.freepascal.org/pipermail/fpc-devel/2019-July/041453.html > Sorry, I missed this one ;(

No problem. It's hard to keep an overview in this thread 😅

Regards,
Sven

Reply by email

Ben Grasset
to Unknown author: procedure foo procedure bar const MultiLine1 = `Sentence one. Another sentence. A third…
PM wrote
one person's PrettyPrint format is another's ugly-as-sin ;)

One last thing: this is generally, as far as I'm concerned, a nitpicky non-reason to exclude a useful feature when you consider the simple fact that anyone who thinks Pascal code at large, in the wild, has any kind of consistent formatting is kidding themselves.

Even FPC, which uses a not-seen-anywhere else GCC-alike style that I can absolutely live with despite the fact that I'm not really a fan of it, does not manage to follow it consistently. The compiler sources are full of files that mix tabs and spaces despite the fact that AFAIK only spaces are ever supposed to be used. There's also a large number of places where you'll find stuff like one-space indentation that makes begin and ends not line up properly, and such. My diff against the trunk version of "scanner.pas" for example appears as though it changes far more than it really does, because while I tried to follow the "FPC style" down to the letter, the fact that various bits of surrounding code did NOT follow it properly made detection of unrelated "changes" unavoidable.

TLDR: In my perfect world, all Pascal code everywhere would be written strictly according to the "Borland Style Guide". I am fully aware that this is not reality, however, and that it never will be, and so I resign myself to the fact that it *does not actually matter that much.*

Reply by email

Tomas Hajny
to Ben Grasset: That said: it may, eventually, be possible for me to add an additional directive taking a…
Ben Grasset wrote 16 lines
On Sat, Jul 6, 2019 at 5:17 PM Ben Grasset wrote: > You cannot, in my opinion at least, reasonably expect something like > this > to *ignore* all indentation and still function in any logical way. > That the > leading whitespace is taken at "face value" is a large part of what > makes > it useful for anything at all. > That said: it may, eventually, be possible for me to add an additional directive taking a number that indicates how many spaces to *remove* from the beginning of a line (but never add.)

.
.

Personally, I don't think that such a directive is worth the effort, because _if_ any indentation should be supported for these strings, it would only make sense to indent them to the same level as the surrounding code (which may differ obviously). From this point of view, a directive allowing to trim leading whitespaces from them would make more sense (but even that is not that much necessary as far as I can tell).

BTW, should you consider creating such a directive, it should probably allow something like the following (to provide means to have a leading space where necessary):

{$MULTILINESTRINGS INDENTED} (* Just invented ;-) *)
const
   MultilineString = `Line 1
                      Line 2
                      `#32`Line 3 with one leading space`;
WriteLn (MultilineString);

... resulting in:

Line 1
Line 2
Line 3 with one leading space

Tomas

Reply by email

Unknown author
to Unknown author: procedure foo procedure bar const MultiLine1 = `Sentence one. Another sentence. A third…
Show quoted text 28 lines
> const MultiLine = > `Sentence one. > Another sentence. > A third sentence. > A fourth sentence. > A fifth sentence.`; procedure foo   procedure bar     const MultiLine1 =           `Sentence one.            Another sentence.            A third sentence.            A fourth sentence.            A fifth sentence.`;           MultiLine2 = `Sentence one.                         Another sentence.                         A third sentence.                         A fourth sentence.                         A fifth sentence.`;           MultiLine3 = `Sentence one. Another sentence. A third sentence. A fourth sentence. A fifth sentence.`;     begin       writeln("MultiLine1= '",MultiLine1,"'");       writeln("MultiLine2= '",MultiLine2,"'");
         (* i forgot to do the line for MultiLine3 *)
         writeln("MultiLine3= '",MultiLine3,"'");
         (* that's what happens when you write directly
            in the email editor without testing *)
Show quoted text 5 lines
    end;   begin     bar;   end; end;
NOTE: No off-list assistance is given without prior approval. *Please keep mailing list traffic on the list unless* *a signed and pre-paid contract is in effect with us.*

Reply by email

Marģers .
to Unknown author

 

----- Reply to message -----
From:
To:

Show quoted text 9 lines
On 7/6/19 4:50 PM, wrote: >       writeln("MultiLine1= '",MultiLine1,"'"); >       writeln("MultiLine2= '",MultiLine2,"'"); (* i forgot to do the line for MultiLine3 *) writeln("MultiLine3= '",MultiLine3,"'"); (* that's what happens when you write directly in the email editor without testing *)

Well, trunk i use still has no string quote
character " .
Maybe it's time add that too while Ben Grasset on
implementing multi line strings? Just kidding...

Reply by email

Unknown author
to Marģers .
Marģers . wrote
Well, trunk i use still has no string quote character " . Maybe it's time add that too while Ben Grasset on implementing multi line strings? Just kidding...

hahahaha! i guess my memory is worse than i thought! :rotflmao:

truth be known, i've been doing a lot of bash, perl, javascript, python3, and other similar coding recently... when i first wrote my message, i had put printf instead of writeln! hahaha! maybe it is just a lack of sleep, though? that or lack of c0ffee :)

NOTE: No off-list assistance is given without prior approval. *Please keep mailing list traffic on the list unless* *a signed and pre-paid contract is in effect with us.*

Reply by email

Ben Grasset

Neat bit of trivia:

Multi line strings even work properly with Ryan's (Ryan Joseph that is) very-cool-but-not-yet-merged-to-trunk
<https://bugs.freepascal.org/view.php?id=35140> generic constants patch.

With a build of FPC that includes both, you can do some really interesting stuff:

program FunWithCurrentlyUnofficialLanguageFeatures;
{$mode ObjFPC}
{$modeswitch AdvancedRecords}
{$modeswitch MultiLineStrings}
type
  generic Tripler<const S: String> = record
    const Result = S + S + S;
  end;

begin
Write(
specialize Tripler<`
A
B
C
D
`>.Result

  );

end.

The above program printing, as you might expect:

A
B
C
D

A
B
C
D

A
B
C
D

Can't do that in Delphi!

Reply by email

J. Gareth Moreton
to Ben Grasset

I'm a bit late to the party again, but the example of an OpenGL shader has won me over, since game design is one thing I enjoy doing.  I guess I'm still a bit unsure how leading and trailing whitespace should be handled, but as long as it's well-documented, I think I'll be happy!

Speaking of shaders, I would request the {$INCLUDESTRINGFILE} thing alongside it, because things like shaders are programs in themselves and may have to be tested in a third-party application, so including the file directly rather than copying and pasting its contents would be much safer if changes need to be made.

Gareth aka. Kit

P.S. Granted, depending on how secure I want to be, I may still have the shader stored in an external file that's loaded at run-time, possibly in an encrypted archive (mostly to help make wall hacks etc. harder to develop), but that's just me.

---
This email has been checked for viruses by Avast antivirus software. https://www.avast.com/antivirus

Reply by email

Michael Van Canneyt
to J. Gareth Moreton
J. Gareth Moreton wrote 10 lines
I'm a bit late to the party again, but the example of an OpenGL shader has won me over, since game design is one thing I enjoy doing.  I guess I'm still a bit unsure how leading and trailing whitespace should be handled, but as long as it's well-documented, I think I'll be happy! Speaking of shaders, I would request the {$INCLUDESTRINGFILE} thing alongside it, because things like shaders are programs in themselves and may have to be tested in a third-party application, so including the file directly rather than copying and pasting its contents would be much safer if changes need to be made.

I think indeed the 2 (`` and directive) should co-exist.

I strongly believe code and text/data should be separate as much as possible. Some of the examples I see makes the hair in my neck crawl... :(

Michael.

Reply by email

Ryan Joseph
to J. Gareth Moreton: I'm a bit late to the party again, but the example of an OpenGL shader has won me over,…
On Jul 8, 2019, at 12:27 AM, J. Gareth Moreton wrote: Speaking of shaders, I would request the {$INCLUDESTRINGFILE} thing alongside it, because things like shaders are programs in themselves and may have to be tested in a third-party application, so including the file directly rather than copying and pasting its contents would be much safer if changes need to be made.

Yeah I wonder if {$INCLUDESTRINGFILE} could leverage the changes with multiline strings so it gets included also. The original patch has been sitting there dead since 2014.

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to J. Gareth Moreton: I'm a bit late to the party again, but the example of an OpenGL shader has won me over,…
AM J. Gareth Moreton wrote 6 lines
Speaking of shaders, I would request the {$INCLUDESTRINGFILE} thing alongside it, because things like shaders are programs in themselves and may have to be tested in a third-party application, so including the file directly rather than copying and pasting its contents would be much safer if changes need to be made.

I'm probably not gonna be working on that myself any time soon, but certainly yeah I think that IncludeString has an equal amount of value as a feature, and would compliment multi-line strings well.

Reply by email

Marco van de Voort
to J. Gareth Moreton: I'm a bit late to the party again, but the example of an OpenGL shader has won me over,…

Op 08/07/2019 om 06:27 schreef J. Gareth Moreton:

Show quoted text 12 lines
I'm a bit late to the party again, but the example of an OpenGL shader has won me over, since game design is one thing I enjoy doing.  I guess I'm still a bit unsure how leading and trailing whitespace should be handled, but as long as it's well-documented, I think I'll be happy! Speaking of shaders, I would request the {$INCLUDESTRINGFILE} thing alongside it, because things like shaders are programs in themselves and may have to be tested in a third-party application, so including the file directly rather than copying and pasting its contents would be much safer if changes need to be made.

I include them now as resources. Windows only atm though

Reply by email

Ben Grasset
to Ben Grasset: On Mon, Jul 8, 2019 at 12:27 AM J. Gareth Moreton I'm probably not gonna be working on…
AM Ben Grasset wrote
I'm probably not gonna be working on that myself any time soon, but certainly yeah I think that IncludeString has an equal amount of value as a feature, and would compliment multi-line strings well.

Hmm, perhaps I spoke too soon. The IncludeStringFile patch looks very simple, actually. Maybe I will in fact take a look at it once I'm properly done with the initial multi line strings implementation.

Reply by email

Ben Grasset

Ok, after thinking about it for a bit, I decided to go ahead and implement the "customizable leading whitespace" thing right away, as a lot of people seemed to want it, and also because I just realized that it would not be difficult at all to do.

So, that said, my Github fork branch
<https://github.com/Akira13641/freepascal> of the compiler now contains a {$MultiLineStringTrimLeft} directive, that does precisely what you might think. Here's one of my compiler tests, which I think demonstrates it fairly well:

program tmultilinestring14;
{$modeswitch MultiLineStrings}
{$MultiLineStringTrimLeft 2}

const A = `
A
B
C
D
`;

{$MultiLineStringTrimLeft 4}

const B = `
A
B
C
D
`;

begin
  Write(A);
  Write(B);

{ The number-to-trim being larger, (even much larger) than the amount of whitespace is not a problem,
as it stops immediately when it is no longer actually *in* whitespace regardless. }

  {$MultiLineStringTrimLeft 10000}
  { Non-leading whitespace is preserved properly, of course. }

Write(`
sdfs
sd fs fs
sd fsfs sdfd sfdf
sdfs fsd

  `);

end.

The output looks like this, showing that everything appears as though it was written at the "far left" of the file without indentation:

A
B
C
D

A
B
C
D

sdfs
sd fs fs
sd fsfs sdfd sfdf
sdfs fsd

Hopefully this will quell some of the uncertainties people may still have had about the feature, and also ultimately make it easier to use overall!

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 8, 2019, at 9:56 PM, Ben Grasset wrote: So, that said, my Github fork branch of the compiler now contains a {$MultiLineStringTrimLeft} directive, that does precisely what you might think. Here's one of my compiler tests, which I think demonstrates it fairly well:

Excellent, now everyone is happy.

Regards,
Ryan Joseph

Reply by email

Ben Grasset

Ok, I think I'm getting close to being ready to open a formal issue on the bug tracker for this feature (will probably do so later today), however, I first wanted to clarify:

Is it preferable if I upload two separate patch files, one containing the actual changes to the compiler sources, and one that adds my tests?

I suspect that this might be the case, especially considering that my tests amount to 22 ".pp" files total (20 programs and 2 units).

Reply by email

Ryan Joseph
to Ben Grasset
On Jul 10, 2019, at 9:53 AM, Ben Grasset wrote: Ok, I think I'm getting close to being ready to open a formal issue on the bug tracker for this feature (will probably do so later today), however, I first wanted to clarify:

Excellent, I have an immediate use for this just today. Hopefully it’s small enough it can get merged without waiting for months. ;)

Regards,
Ryan Joseph

Reply by email

Ben Grasset
to Ryan Joseph
PM Ryan Joseph wrote
Excellent, I have an immediate use for this just today. Hopefully it’s small enough it can get merged without waiting for months. ;)

Hopefully! I'll keep my branch up to date with trunk regardless, though.

Reply by email

Ben Grasset
to Ben Grasset: On Sat, Jul 6, 2019 at 2:15 AM Tony via fpc-devel < I think you are certainly doing…
AM Ben Grasset wrote 30 lines
On Sat, Jul 6, 2019 at 2:15 AM Tony via fpc-devel < > wrote: > On Thu, 4 Jul 2019 12:00:07 +0200 > Marco van de Voort wrote: > > > In conclusion: it is a solution in search of a problem, with bad > > behaviour in errorhandling (when unbalanced the compiler errors on > > perfectly fine code in the wrong place after whatever ' closes the > > unbalanced ) on top of it. > > > > This is why the feature goes against the grain of Pascal IMHO. > > Well said Marco! I have been reading this mailing list for some time > and have been disturbed recently-ish by how often suggestions come up > for "my pet feature from another language" or "a cool idea I just > had" (I am probably doing an injustice to some of the suggestions, but > often they feel deeply un-Pascal-ish - I can't define it but I know it > when I see it). In these circumstances, a healthy scepticism and > conservatism among the development team is a good thing. > I think you are certainly doing injustice to a lot of things. Furthermore, you realize it is possible, to just, you know, make the compiler give better errors when necessary / desired? I intend to add something like this for unterminated multi-line strings, most likely once I'm done writing my tests and have submitted a formal patch on the bugtracker.

I've now actually done this, for the record:

https://bugs.freepascal.org/view.php?id=35827#c117278

Reply by email