How do I create a specially delimited command in `xparse`

How do I create a specially delimited command in `xparse`



Using def I can define a command as follows:


def


defaecmd#1 located at (#2);---definition---



I can recreate this with xparse as follows:


xparse


NewDocumentCommandaecmd u~located~at~(u);----definition---



However, I have a situation where I want to be able to write a command with an (almost final) optional argument. This would be a pain in the neck to do with def.


def



I'd like a command which could be expressed as either


aecmdManditory content[optional content] located at (location);



or


aecmdManditory content located at (location);



Essentially, I would like something that works like r but instead of taking a single token as the delimiters can take whole strings. Let's call this hypothetical argument specifier b


r


b



Then my desired command could be defined along these lines:


NewDocumentCommand{ mob~located~at~(); ---something---



I'm aware I could write something like that following:


NewDocumentCommandaecmd{ mou~located~at~(u);---definition---



Further, I suppose that I could test whether or not something was passed in the 3rd argument and raise an error if there was anything there.

But this just seems clunky. It doesn't feel right to me.



Any suggestions about how to do this better?




2 Answers
2



xparse? Pshaw!


xparse



EDITED to capture syntax error if optional argument is unbracketed.


documentclassarticle
usepackageparskip

newcommandaecmd[1]defmandatory#1aecmdaux
defaecmdaux#1 located at (#2);deflocation#2aecmdauxA#1
newcommandaecmdauxA[1]setbox0=hbox%
if[#1[gdefnextaecmdauxB#1else gdefnextsyntax errorfi%
next%

newcommandaecmdauxB[1]%
Optional: #1\ Mandatory: mandatory\ location: location

begindocument
aecmdColonel Mustard located at (the library);

aecmdColonel Mustard[with a wrench] located at (the library);

aecmdColonel Mustard on 4th street located at (the library);
enddocument



enter image description here



If one does not like the output of "syntax error" then in the definition of aecmdauxA, the words "syntax error" can be replaced with aecmdauxB and the effect will be to ignore the stray words in the syntax, while still producing the mandatory and location arguments.


aecmdauxA


aecmdauxB





+1 This is clever. I like it. But, it allows the user to do somehting like aecmdColonel Mustard on 4th street located at (the library); and might not notice that this is creating spurious output.
– A.Ellett
Aug 30 at 19:17


aecmdColonel Mustard on 4th street located at (the library);





@A.Ellett I designed it based on your two specified input syntax variations provided in the question. What you just gave in the above comment does not fit that form...how should such a thing be digested? Are you implying that optional content should not be specified in brackets?
– Steven B. Segletes
Aug 30 at 19:24






What I'm saying is if something is passed as a 2nd argument that's not in square brackets, then the syntax should be wrong. Anyhow, I do like your solution. It just doesn't catch an input error if the 2nd argument isn't in square brackets.
– A.Ellett
Aug 30 at 19:27





@A.Ellett So, to be clear, the 2nd argument should be in brackets, but if it is not, you would like an error generated? Or do you want all the non bracketed content to be taken as the optional argument? I can do that pretty easy.
– Steven B. Segletes
Aug 30 at 19:29






I wouldn't like using nonbracketed content as the optional argument. But, if you've got more tricks that I'm unaware of about generating an error: do by all means share.
– A.Ellett
Aug 30 at 19:32



With xparse, but I find such syntax a very bad idea, notwithstanding TikZ using it.


xparse


documentclassarticle
usepackagexparse

ExplSyntaxOn
NewDocumentCommandaecmdmoulocated~at~(u);

tl_if_blank:nF #3 ERROR
noindent
#1~(mandatory)\
IfValueT#2#2~(optional)\
#4~(final)

ExplSyntaxOff

begindocument

aecmdMandatory content[optional content] located at (location);

aecmdMandatory content located at (location);

aecmdColonel Mustard on 4th street located at (the library);

enddocument



enter image description here



Note that the third call raises an error.





Actually, TikZ is the reason for me using this sort of syntax. So you're solution is basically the same as my wonky approach. Though I hadn't thought of testing for non-blank.
– A.Ellett
Aug 30 at 20:23


TikZ





@A.Ellett xparse is not the best for this. See how TikZ does, instead.
– egreg
Aug 30 at 20:25


xparse



Required, but never shown



Required, but never shown






By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Popular posts from this blog

𛂒𛀶,𛀽𛀑𛂀𛃧𛂓𛀙𛃆𛃑𛃷𛂟𛁡𛀢𛀟𛁤𛂽𛁕𛁪𛂟𛂯,𛁞𛂧𛀴𛁄𛁠𛁼𛂿𛀤 𛂘,𛁺𛂾𛃭𛃭𛃵𛀺,𛂣𛃍𛂖𛃶 𛀸𛃀𛂖𛁶𛁏𛁚 𛂢𛂞 𛁰𛂆𛀔,𛁸𛀽𛁓𛃋𛂇𛃧𛀧𛃣𛂐𛃇,𛂂𛃻𛃲𛁬𛃞𛀧𛃃𛀅 𛂭𛁠𛁡𛃇𛀷𛃓𛁥,𛁙𛁘𛁞𛃸𛁸𛃣𛁜,𛂛,𛃿,𛁯𛂘𛂌𛃛𛁱𛃌𛂈𛂇 𛁊𛃲,𛀕𛃴𛀜 𛀶𛂆𛀶𛃟𛂉𛀣,𛂐𛁞𛁾 𛁷𛂑𛁳𛂯𛀬𛃅,𛃶𛁼

Edmonton

Crossroads (UK TV series)