top of page

How to extend Gemini power in Flutter with FunctionCall

Writer: Suesi TranSuesi Tran

Introduction

In the previous two posts, we explored how to integrate Gemini with Flutter for text-based prompts and file-based inputs. If you haven’t checked them out yet, you can find them here:

Now, let’s take Gemini’s capabilities even further by leveraging FunctionCall. This feature allows Gemini to interact with external functions, perform calculations, fetch data, and even trigger real-world actions — all from within your Flutter app!


By the end of this post, you’ll learn:

✅ How to define and register a function for Gemini✅ How to call that function dynamically through FunctionCall✅ How to handle function responses in Flutter

With this, you can extend the power of Gemini beyond simple text-based AI and make it an intelligent assistant that actually executes tasks for you. Here’s a use-case we’re working on today.


Use Case: Get a defined name for Gemini to be used in this application

Imagine you’re building a smart assistant in your Flutter app. You want users to ask something like:

“What’s your name?”

Instead of just returning a name like “Gemini”, we’ll make Gemini call a real function to:

Get the defined name we want Gemini to use which will return a String with name “Super Funny Name”

Let’s dive in!


Implementation

Step 1: Setup Tool with list of functionDeclarations

Before we can make Gemini retrieve a customised name, we need to define a function that return this customised name, so that Gemini knows when to call it.First, we need to update the initiation of GenerativeModel to include Tool object, with a definition of our first function

  final GenerativeModel _model = GenerativeModel(    model: 'gemini-1.5-pro',    apiKey: geminiApiKey,    tools: [      Tool(        functionDeclarations: [FunctionDeclaration(          // function name          "getFriendlyName",          // function description          "Retrieves the friendly name for Gemini model to be used in this application",          // Schema for Function's parameter          null        )]      )    ]  );

In which:

  • getFriendlyName is the name of the function, and Gemini will use this name in FunctionCall when it request for a function execution

  • Function description is a clear description to tell Gemini what this function is for, when it is needed, so it will help Gemini to decide when to request this function

  • Function Schema is a Schema of all function’s input parameters. My trick here is to always use Schema.object even if function requires only 1 input param, because the param will be returned in FunctionCall as a map of arguments, so the Schema.object allows us to define the name for each param, therefore it’s easy to get the value for each param from the map later.

Now that we’ve registered the function, the next step is to implement it so that when Gemini calls it, we can return our “Super Funny Name”

Let’s move on to Step 2: Implement getFriendlyName Function 🚀


Step 2: Implement getFriendlyName Function

Now that we’ve registered the function in Gemini, we need to implement it so that when Gemini is asked:

“What’s your name?”

It won’t just reply “Gemini”, but instead, it will call our function to get a predefined name (e.g., “Super Funny Name”).

Implement the Function

Since this is a simple function that just returns a static string, we can implement it like this

/// This function will return the string "Super Funny Name"Future<String> getFriendlyName() async {  return 'Super Funny Name';}

What This Does

  • When Gemini receives a question like “What’s your name?”, it will trigger getFriendlyName().

  • Instead of responding with its default name, Gemini will call this function and return "Super Funny Name"

Example Interaction

User Input:

“Hey, what’s your name?”

Gemini’s Response:

“My name is Super Funny Name! Nice to meet you!”

Now that we have our function ready, let’s move on to Step 3: Calling the Function from Gemini 🚀


Step 3: Calling the Function from Gemini

Now that we have implemented getFriendlyName(), we need to connect it to Gemini’s Function Calling so that when a user asks "What’s your name?", Gemini will trigger our function instead of answering on its own.


Handle FunctionCall in Flutter

Now, we need to update our sendMessage function to handle FunctionCalls in the response:

Future<String> sendMessage(String prompt) async {
  final List<Part> parts = [TextPart(prompt)];
  Content content = Content('user', parts);
  try {
    // Send the message and get the response.
    GenerateContentResponse response =
      await _chatSession.sendMessage(content);

    // get all FunctionCall from response candidate
    final List<FunctionCall> functionCalls = response.candidates
        .map((e) => e.content.parts.whereType<FunctionCall>().toList(),)
         .fold([],(previousValue, element) => previousValue..addAll(element),
      );

    // only invoke function if FunctionCall is requested by Gemini
    if (functionCalls.isNotEmpty) {
      for (FunctionCall functionCall in functionCalls) {
        if (functionCall.name == "getFriendlyName") {
          final FunctionResponse response = FunctionResponse(
            'getFriendlyName', {'friendlyName': await getFriendlyName()});

          // add this response into parts, to be sent back to Gemini later
          parts.add(response);
        }
      }

      // after all functions are called, update the content with new parts,
      content = Content('user', parts);
      // and send this content with function response back to Gemini
      response = await _chatSession.sendMessage(content);
    }

    return response.text ?? "No response from AI.";
  } catch (e) {
    return "Error: $e";
  }
}

Result

Gemini’s Internal Processing:

  • Gemini detects that it should call "getFriendlyName" instead of answering directly.

  • Gemini triggers our function and waits for the response.


🎯 What’s Next?

Now that we’ve successfully implemented Function Calling, you can extend this by:✅ Defining more functions for different assistant capabilities✅ Expanding to multi-turn conversations where Gemini remembers past interactions.

💡 And that’s it! We’ve just extended Gemini’s power in Flutter using Function Calling! 🚀


Conclusion 🎉

In this post, we explored how to extend Gemini’s capabilities in Flutter by leveraging Function Calling. Instead of having Gemini respond with generic text, we made it call real functions to fetch dynamic responses.

We covered:✅ Setting up Function Calling in Gemini✅ Implementing a function (getFriendlyName) to return a predefined assistant name✅ Connecting everything so Gemini calls our function when needed


What’s Next?

With Function Calling, you can go beyond static responses and build powerful AI assistants that interact with real-world data. Here are some ideas to expand further:

💡 More Functions: Let Gemini handle multiple tools like fetching weather, checking calendars, or generating random jokes.💡 Multi-turn Conversations: Let Gemini remember past interactions and give contextual responses.💡 Integrate with APIs: Use Function Calling to connect Gemini with external APIs, like real-time news, stock prices, or smart home controls.

This concludes our three-part Gemini + Flutter series 🎉 But AI in Flutter doesn’t stop here — stay tuned for more exciting use cases! 🚀

Sounds fun right? But….


Waittttttttttttt! 🚨

Before you go ahead and call Gemini API directly in Flutter, take a look at this:

🚨 Warning! Calling Gemini API directly from Flutter might expose your API key! Google recommends this approach for prototyping only. But if you want to use Gemini in production, then…

🔥 Stay tuned for Part 4: Deploy Gemini API securely with Vertex AI API on Cloud Functions!

No more API key exposure, just better security & scalability 🚀 See you in the next post! And if you enjoyed this post, feel free to buy me a coffee!




 
 
 

Recent Posts

See All

Komentarji


Subscribe Form

Thanks for submitting!

  • Facebook
  • LinkedIn

©2023 by SuesiTran.

bottom of page