There are several shortcomings in your definition. You need to first absorb the argument to \ref
and only after it check whether a c
follows.
Also the conditional should end before calling the “gobbling” macro.
Finally, \ref
gets redefined by hyperref
at begin document, so your own redefinition should be delayed.
Another small issue is the usage of \let
with the \ref
command that hyperref
makes robust; here I use \NewCommandCopy
that's been available for more than a year; if your TeX distribution is older, use \LetLtxMacro
from the letltxmacro
package.
\documentclass[10pt]{article}
\usepackage{amsthm}
\usepackage{hyperref}
\usepackage{cleveref}
\newtheorem{theorem}{Theorem}
\makeatletter
\AtBeginDocument{%
\NewCommandCopy{\old@ref}{\ref}%
\def\ref#1{\def\temp@ref{#1}\futurelet\@nexttoken\new@ref}%
}
\def\new@ref{%
\if c\noexpand\@nexttoken
\expandafter\@firstoftwo
\else
\expandafter\@secondoftwo
\fi
{\cref@eatc{\temp@ref}}%
{\old@ref{\temp@ref}}%
}
\def\cref@eatc#1c{\cref{#1}}
\makeatother
\begin{document}
\begin{theorem}[sdfs] \label{sdf} asfa \end{theorem}
\cref{sdf} = theorem 1
\ref{sdf}c = theorem 1
\ref{sdf} c = 1 c
\end{document}

Why \noexpand
? Because you don't want to expand the following token which might be a macro or ~
.
You may appreciate an expl3
version of the same, which is easier to implement, but not conceptually different.
\documentclass[10pt]{article}
\usepackage{amsthm}
\usepackage{hyperref}
\usepackage{cleveref}
\newtheorem{theorem}{Theorem}
\ExplSyntaxOn
\AtBeginDocument
{
\NewCommandCopy{\__refc_saved_ref:n}{\ref}
\cs_set_eq:NN \ref \__refc_new_ref:n
}
\tl_new:N \l__refc_arg_tl
\cs_new_protected:Nn \__refc_new_ref:n
{
\tl_set:Nn \l__refc_arg_tl { #1 }
\peek_charcode_remove:NTF c
{
\exp_args:NV \cref \l__refc_arg_tl
}
{
\exp_args:NV \__refc_saved_ref:n \l__refc_arg_tl
}
}
\ExplSyntaxOff
\begin{document}
\begin{theorem}[sdfs] \label{sdf} asfa \end{theorem}
\cref{sdf} = theorem 1
\ref{sdf}c = theorem 1
\ref{sdf} c = 1 c
\end{document}