I can't parametrize babel's \foreignlanguage command

Unfortunately several commands from xstring are not fully expandable. You need to use each case of \IfStrEqCase to define a helper macro storing the appropriate value. Here is one way to do this:

Sample output

\documentclass{article}

\usepackage[french,dutch]{babel}
\usepackage{xstring}

\newcommand{\expandlangabbr}[2]{\IfStrEqCase{#1}%
  {{fr}{\xdef#2{french}}}%
  [\xdef#2{dutch}]}

\newcommand{\said}[2][nl]{\expandlangabbr{#1}{\mylang}%
  \foreignlanguage{\mylang}{\textit{``#2''}}}

\begin{document}

\said{Niets}

\said[fr]{Rien}

\end{document}

You need something that fully expands to a language name, but \IfStrEqCase only provides the instructions to typeset it.

You can use an expandable version provided by xparse.

\documentclass[]{article}
\usepackage[T1]{fontenc}
\usepackage[french,dutch]{babel}

\usepackage{xparse}

\ExplSyntaxOn
\NewExpandableDocumentCommand{\xIfStrEqCase}{mmm}
 {
  \str_case:nnF { #1 } { #2 } { #3 }
 }
\ExplSyntaxOff

\newcommand{\said}[2][nl]{%
  \foreignlanguage
    {\xIfStrEqCase{#1}{{fr}{french}}{dutch}}
    {(\languagename) \textit{``#2''}}%
}

\begin{document}

\said{Niets}

\said[fr]{Rien}

\end{document}

The \xIfStrEqCase macro takes three argument, like \IfStrEqCase, but the trailing one is mandatory.

\xIfStrEqCase{<string>}{{<string-a>}{code-a}...}{<default code>}

I added to the code (\languagename) just for being sure what language has been selected.

enter image description here

Tags:

Macros

Babel