How to add quotes to lines of text added to [text] object?

ygreq's icon

Hi folks!

I am trying to figure out how to add quotes for each line of text I am adding to [text].

Any suggestions?

Max Patch
Copy patch and select New From Clipboard in Max.

Andy Maskell's icon

Quotation marks are one of the "special" characters in Max and are processed in most objects rather than taken as literal characters. To have the quotation marks included as part of the literal string in each message, you will have to precede each quote mark with a backslash thus:

\"Line 1\"

Hope that helps?

ygreq's icon

Thank you, Andy!
Yes, I forgot!

What I actually wanted was to also automatically add quotes to each line added. Pseudocode would be something like this: Insert text line -> add quotes -> add it to [text]

Any suggestion regarding this?
Thank you so much!

Andy Maskell's icon

tosymbol appears to do the trick:

Andy Maskell's icon

Oh no, hang on, it doesn't work for text input! I'm trying to think how sprintf could do this.

Andy Maskell's icon

I can get sprintf to work with single quotes but I'm darned if I can find a way to make it work with double quotes:

The problem is that double quotes are a special character in C++ as well, which sprintf is derived from, but \" gets stripped off again after formatting with sprintf.

Andy Maskell's icon

I've set a request to support to see if they have any ideas as I'd love to know how to do this.

And it might even be a bug in the way that sprintf works!

ygreq's icon

Yeap. :/ It seems I need double quotes. Here is what I am trying to achieve. I have a small program for creating subtitles. But not any kind of subtitles. You input normal text with lines of text for each dialogue. And then that text is formatted so that you separate each line of text word for word. So that instead of showing each line of text one by one, to show each line of text like this. It shows the first word, then the second word is added, then the third word is added and so on until the line of text is finished and then on with the second one.

The whole problem with quotes is that I need to add quotes for each line of text so that commas (,) in text are taken into consideration. I need a way to automate adding quotes. I didn't fix this yet. So the solution until then would be to edit the whole text to add quotes for each line of text. That would be a lot of work.

Here is what I am working on

Max Patch
Copy patch and select New From Clipboard in Max.


subs_with_quotes.txt
text/plain 0.35 KB

subs_no_quotes.txt
text/plain 0.33 KB

Andy Maskell's icon

YEAH!!! I have found a way to do it!!!:

ygreq's icon

Niiiiice!!!! Thank you so much, Andy! This definitely fixes the problem!!!

ygreq's icon

This is the new patch:

Max Patch
Copy patch and select New From Clipboard in Max.

ygreq's icon

Hmm. Now I realize that the example you gave adds quotes but does not save the comma. Which was the whole point of this :/

Andy Maskell's icon

Cool! Good luck with it. Glad I could help.... eventually!

ygreq's icon

Here is a simplified version of the patch which includes only the necessary objects, the part where you input the normal lines of text and the part where is should add quotes while keeping the commas. Unfortunately it does not keep the commas. :/

Max Patch
Copy patch and select New From Clipboard in Max.

Andy Maskell's icon

Darn! It's treating the comma as a delimiter. Putting a backslash in front of each comma works:

but I guess you're now going to want that to be automated too!

ygreq's icon

I know about that unfortunately. The whole deal with the quotes was not to start adding forward slashes before each and every comma in the whole text. :/

Andy Maskell's icon

Ah yes, I see! I'm still working on it!!!

ygreq's icon

Thank you for looking into it, Andy. I am lost. For now anyway.

Andy Maskell's icon

Ok, I've come up with this:

The problem I had was handling things differently depending on whether the text clip had a comma in it or not. So this ends up doing both jobs - keeping the commas and adding the quotes.

And then I thought, "What if there are more commas"! As it is, it can handle 0, 1 or 2 commas but you could scale it up if you wanted to cover more!

What you will have to do though is to see how it copes when you fire a whole file of clips at it. You might have to slow the reading down a bit somehow.

Max Patch
Copy patch and select New From Clipboard in Max.

👽'tW∆s ∆lienz👽's icon

☝️😆😆🤣🤣... made me think of that scene from 'The Shining'👇😅

😂

Andy Maskell's icon

😂🤣😂 It was important for me to test that it could decode and process things fast enough without tripping over itself. You’d have thought what he needed was really simple to code but it was actually a nightmare finding a way to add quotes without loosing the commas!

Max really doesn't handle strings very well!

(And I sincerely hope @YGREQ sees this and makes use of it after all the hours I put in to finding a solution!)

👽'tW∆s ∆lienz👽's icon

Max really doesn't handle strings very well!

Haha, i know the feeling well(never found it fun to work with text in any environ); was watching this thread, wondering about all the text objects 'regexp', 'sprintf', 'tosymbol', then i see 'combine' does even more... it's a relief to see your solution, that's a great one 🙌

Andy Maskell's icon

Pascal was good at strings and even Fortran could have handled this better. And let's not forget good old BASIC!

The problem with Max is that it treats a comma as a delimiter in messages so whilst sprintf could add the quotes, everything fell over when there were commas in the string as that immediately cut the strings into pieces. So I had to find a way to count the number of pieces and reassemble them - and in the right order - hence the use of zl.stack

ygreq's icon

Oh My God, Andy!

You're the greatest!! I will test your solution asap in the patch I am working!!

And indeed! Andy is clever, really clever!!!!

Andy Maskell's icon

Don’t forget that your text file input needs to trigger both the tosymbol and the bang next to it at the same time. The zlclear is there just in case things get out of sync but you could trigger that as well if necessary.

I sincerely hope it works this time! Even the support team were stumped by this one!

Andy Maskell's icon

Also, I don’t know why I put list in the last combine object. It can actually be anything you like as it’s just a placeholder. Something like text might be more logical.

Source Audio's icon

And what if text is

is Andy ; really clever ? , or not ; ?

Andy Maskell's icon

So what's your solution then?

The request was to find a way to surround normal text strings containing commas with double quotes for a subtitle routine, not find ways to process strings containing all manner of odd punctuation and irregular spacing! If he had asked for that, I would have found a way to code for it!

Roman Thilenius's icon


the general approach makes sense and is for this kind of stuff my only solution, too: before you get confused about characters vs max messages or what object does what to a message, just split the whole string into symbols of characters, one by one.

consequently, keyboard input of such strings should also happen one by one - i.e. forget using objects other than [key] for that.

where required, you can still collect these symbols into a list or atoi/itoa them.

if the input is already a textfile, then it is getting a bit more complicated of course.

Andy Maskell's icon

The input was indeed coming from a text file, hence the problem. I just used messages in my example solution as I didn't have the text file to play with at the time. (And I couldn't think of anything better to come up with after many hours of effort to show that it worked!)

Source Audio's icon

try for example this

Max Patch
Copy patch and select New From Clipboard in Max.

Andy Maskell's icon

Nice try but it doesn't work on his text files and it won't work with the subtitles routine.

Andy Maskell's icon

@YGREC I've updated my routine a bit so that it loads the unquoted text file and processes it all automatically on loading the patch. I also had to add a few bits as I had tested it on the quoted file by mistake and it didn't work properly on the unquoted one as it was! Max now wanted to put "set" in front of all the lines of text!!!

I hope that it's not too late for this!

Max Patch
Copy patch and select New From Clipboard in Max.

Source Audio's icon

@ AndyMaskell

All your posted examples will fail if semicolon is in the text.


For that reason I see them unusable .

What Max version are you using ?

My example is for Max 8.
there is only one bug in atoi object in Max :
comma will allways get space prepended at output,
if it does not exist.
like a, b == ASCII 97 44 98
atoi output 97 32 44 98 back to itoa a , b
this is what my example outputs from original text file:

In most cases that causes no big harm.

Now here is new challenge for your research, how to get
that inserted space removed in that condition using a single max object

above is original text, below output without false inserted space

Andy Maskell's icon

Well, rather than playing silly games with me, perhaps you could enlighten the nice person who presented the problem in the first place!

Andy Maskell's icon

regexp @re "32 44" @substitute 44

We're all learning you know, @Source Audio!

Oh, and I'm on Max 8.2.2 for what it's worth.

By the way, I was randomly looking through some of your previous replies and found that you've already given answers to problems like this before. Pity you couldn't have chipped in right at beginning rather than coming along later and picking holes in other peoples' attempts to assist (and learn).

Source Audio's icon

Wonderfull, good guess.

This is no silly game at all, but a point that one has to be
a bit more concerned when advicing others...
that is all.
------
The real problem here is, that even one would trust one
or the other object does exactly what it aims to,
it is not true all the time.

Max has it's own head when it comes to text, because
max is no text editor at all.
We are all happy in many cases that it is so.

It is more advisable to get that text files max conform outside of max in first place.
There are many text tools in both mac and windows world, where you can batch edit
thousands of files and lines, like to add double quotas to each line, instead of
fighting that battle in max itself.

Andy Maskell's icon

So @YGREC, after @Source Audio's little game, we get this:

Max Patch
Copy patch and select New From Clipboard in Max.

ygreq's icon

I was busy with other things and did not look further into this. You really streamlined the whole process. Thank you so much, Andy.

And to Source Audio, I believe Andy is right. I consider we are learning from each other. And I believe that any suggestion or idea is truly appreciated because even if it does not give you a full answer, it helps a lot none-the-less. Anyway, thank you all for looking into this. And once again thank you so much, Andy, for everything!

Andy Maskell's icon

You're welcome!

ygreq's icon

Ah! BTW next thing was to output each phrase one word at a time. I already did it. But I am curious if you would suggest better ways of doing it.
Here is the patch:

Max Patch
Copy patch and select New From Clipboard in Max.


And now I am thinking of doing the same thing, but the output would take into consideration the length of the words and outputting each word based on that.

I will let you know how that goes.

ygreq's icon

I forgot to mention I still have an issue if a phrase ends with 2 or more punctuation marks. I get a space in between the punctuation marks. But that is not a big problem.

I might try to use [regexp] somehow later on.

ygreq's icon

Related to want I want to achieve, the longer the word, the more it stays after it is written. Because it looks to mechanical how it is now.

The whole idea is to try to imitate automatic translators like you see in apps like Google Meet.

ygreq's icon

Ok. I've done what I wanted to achieve. It is a bit convoluted, but it works. I don't like the fact that I use a [delay]. I dislike this object quite a lot. And the bug with the punctuation marks is still there. But here is the code. Let me know what you think.

Max Patch
Copy patch and select New From Clipboard in Max.

Andy Maskell's icon

It's looking good. The only bit I'm not sure about is why you are looking for the punctuation marks? That's where the split at the end of line 1 occurs, for example. If you are using the space (32) to separate words then why do you also need to scan for the punctuation? All you need to put in there is something that flags up that the end of the line has been reached.

One way I've thought of is to feed the output of the first atoi into a zl.len object and use that number to prime a counter that is triggered by each letter passing through the iter object. Once the counter reaches the value given by the zl.len it triggers the start of the output sequence (my bits are in red):

With this method, all the punctuation appears correctly without any extra gaps.

ygreq's icon

Hmmm. It looks like it is the right path. But it creates a new problem now. The first phrase I try to input does not give any results. And then the next phrase I input shows the last word of the previous phrase. Everything starts to work from the 3rd phrase forward.

Maybe I did something wrong. I will look further. But here is the patch:

Max Patch
Copy patch and select New From Clipboard in Max.

ygreq's icon

I see now that the last word that is input when starting up the patch is not the last word of the phrase, but the penultimate. And this is how the problem starts.

Andy Maskell's icon

I can see now that the counter is not being initialised properly the first time around. Try replacing the red items here with the green patchcord:

I think that fixes it.

Source Audio's icon

you guys still struggle with that ...

Max Patch
Copy patch and select New From Clipboard in Max.


here another approach using filein

Max Patch
Copy patch and select New From Clipboard in Max.

Andy Maskell's icon

Nope, we're well past that stage! This is about displaying the subtitles in a certain way.

Source Audio's icon

maybe you need a video to see what is going on?

showsubs.mov
video/quicktime 3.36 MB

Andy Maskell's icon

OK, I see what you mean.

Over to you @YGREQ.

Roman Thilenius's icon


i wonder what you guys think the text object thinks when it gets "one two three".

will it be able to later supply you with the complete string as a symbol if you ask it too?

i dont think so.

ygreq's icon

@Andy! Thank you, Andy! That solves it elegantly
@Source Audio. Interesting approach indeed. Thank you!!
@Roman. Sorry. I don't get it. :/

Source Audio's icon

Interpretation of what Roman explained in few words :

Max will allways limit you when displaying text.
for example this :
"my prefered coctail fruits are \apples - bananas\ or \oranges - kiwi\"
there is no way I know of reading that line as is
and output or print it into anything in max.
adding quotas to this line :
my prefered coctail fruits are \apples - bananas\ or \oranges - kiwi\
would work only using filein which reads byte by byte, not taking care about what it reads.
and add it into text object.
But then - no way out .
one would have to internaly escape backslash with another one
"my prefered coctail fruits are \\apples - bananas\\ or \\oranges - kiwi\\"
then text could print or output into comment
my prefered coctail fruits are \apples - bananas\ or \oranges - kiwi\
but not output to message, textedit or any other max object which is aware of max specific
meta characters.
-----------
I suggested comment instead of message because comment has no output,
and so does not modify input .


ygreq's icon

Thank you for clarifying this, Source Audio.