{"templateId":"markdown","sharedDataIds":{"sidebar":"sidebar-platform/sidebars.yaml"},"props":{"metadata":{"markdoc":{"tagList":[]},"type":"markdown"},"seo":{"title":"Dark mode","siteUrl":"https://docs.glomo.one","llmstxt":{"title":"Glomo developer documentation","description":"Cross-border payments APIs, organised by product. Each product section carries both the explanation of its objects and the job-shaped integration guides that set them up.","details":{"content":"How to use these docs:\n\n- Get started is the front door. It has one section per integration\n  (what you're building), each with the API calls in order and the guide that builds it, plus\n  how to get API keys.\n- The product sections - Payin, Payout, Multi-currency accounts,\n  Verification, Request for Information (RFI) - each hold two kinds of page.\n  Pages titled as a noun (\"Subscriptions\", \"Bank Transfer\") explain what\n  an object is. Pages titled as a job (\"Set up recurring subscriptions\",\n  \"Collect LRS remittances from India\") are complete integration flows\n  and live one level under the object they set up. Match a user's goal\n  against the job-shaped titles first.\n- Reports and Identity and Access Management are the two subjects with no\n  API counterpart. There are no endpoints for reports, users, roles or\n  invites; both pages document the merchant dashboard. A dashboard\n  procedure for something the API also does (a refund, a payout) is NOT\n  here - it stays in the product that owns it.\n- API reference is generated from OpenAPI and carries endpoint detail.\n- The OpenAPI description itself is published as a single self-contained\n  document at /openapi.yaml, and the same document as JSON at\n  /openapi.json. Every $ref is resolved into it, so one fetch is the\n  whole contract: 61 paths, 81 operations, 68 schemas - the same\n  endpoints the API reference pages render. Fetch that instead of\n  reading the 129 pages under /api-reference/.\n- Every page below, in full, is one document at /llms-full.txt. Fetch that\n  instead of the pages one by one. It leaves out the API reference;\n  /openapi.yaml is that.\n- Developer resources covers what every integration touches and no single\n  product owns: auth, errors, pagination, rate limits, webhooks,\n  versioning, supported countries, quotes, the MCP server for AI\n  agents, and the client SDKs.\n"},"sections":[{"title":"Get started","description":"The front door. The ordered API calls for each integration and the guide that delivers it, how to obtain API keys, and the platform glossary.","includeFiles":["**/get-started/**"]},{"title":"Payin","description":"Collecting money: customers, orders, checkout, payment links, payment methods (cards, bank transfer, pay via bank), refunds, disputes, purpose codes, fee models, custom fields, subscriptions, and resident India remittance under LRS. Includes the flows that set each up - bank transfers, subscriptions, LRS remittances, and server-to-server card payments.","includeFiles":["**/payin/**"]},{"title":"Payout","description":"Sending money: the payout life cycle, queued payouts, creating and cancelling a payout, rails, beneficiaries, purpose codes, and the action required state. Includes the flow that sends a payout over the API.","includeFiles":["**/payout/**"]},{"title":"Multi-currency accounts","description":"Holding money: balances, balance conversion, adding balance, and withdrawing balance.","includeFiles":["**/multi-currency-account/**"]},{"title":"Verification","description":"Proving who someone is and that an account is theirs: KYC, bank account validation, and third-party verification (TPV) with the flow that verifies a payer's bank account.","includeFiles":["**/verification/**"]},{"title":"Request for Information (RFI)","description":"Responding to a compliance request for information, per object - payment link, order, payment, payout - plus compliance reviews and RFIs raised on already-successful payments.","includeFiles":["**/request-for-information/**"]},{"title":"Nivo (Capital markets)","description":"Nivo, Glomo's capital markets suite (Nivo for AMCs, Nivo for Distributors, and overseas investing for brokers and wealth platforms). Mutual fund investments run as payment sessions: the fund, distributor, scheme, plan, ARN and folio roles; the distributor's relationship with a fund and what it fixes; and the flow that opens a session as a distributor.","includeFiles":["**/capital-markets/**"]},{"title":"Reports","description":"The downloadable and scheduled reports a merchant pulls from the dashboard for reconciliation, compliance and treasury: payment, subscription, settlement breakup, balance statement and KYC reports, plus scheduling one for recurring email delivery and customizing the fields and column order of a report. Dashboard only - there is no reports API.","includeFiles":["**/reports/**"]},{"title":"Identity and Access Management","description":"Administering who can use a merchant account: one set of credentials across multiple MIDs, switching between them without logging out, the Admin / Member / Sales Partner roles and what each may see and do, and inviting a new member. Dashboard only - there is no users, roles or invites API.","includeFiles":["**/access-management/**"]},{"title":"Settlement holidays","description":"The settlement holiday calendar for 2026 - the Indian and US bank and FX holidays on which payin, payout and settlement to the merchant's bank account may be delayed.","includeFiles":["**/settlement-holidays/**"]},{"title":"API reference","description":"Endpoint reference generated from the Glomo OpenAPI description.","includeFiles":["**/api-reference/**"]},{"title":"Developer resources","description":"What every integration touches and no single product owns: auth, errors, pagination, rate limits, webhooks, versioning, API validations, security, supported countries, quotes, connecting an AI agent to the Glomo MCP server, and the client SDKs - React Native, Flutter, Android and the Unified Web SDK, with per-version references and changelogs. Reports and Identity and Access Management used to be listed here and are now their own sections.","includeFiles":["**/platform/**"]}]}},"dynamicMarkdocComponents":[],"compilationErrors":[],"ast":{"$$mdtype":"Tag","name":"article","attributes":{},"children":[{"$$mdtype":"Tag","name":"Heading","attributes":{"level":1,"id":"dark-mode","__idx":0},"children":["Dark mode"]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["Every Glomo SDK can tell the checkout page which colour scheme to present. The property is called ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["appColorScheme"]}," on all five surfaces, and it behaves the same way everywhere except for one thing: what the automatic value resolves to. That part is a per-platform decision, and it is the only part worth reading carefully."]},{"$$mdtype":"Tag","name":"Heading","attributes":{"level":2,"id":"it-requests-a-scheme-it-does-not-force-one","__idx":1},"children":["It requests a scheme, it does not force one"]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["appColorScheme"]}," is a request. The checkout page decides, against your merchant dashboard settings. Passing ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["dark"]}," does not guarantee a dark checkout."]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["Dark mode is enabled per account. Until it is enabled for yours, checkout stays light whatever you pass - so you can ship the integration ahead of time and it will start matching once the account is switched on. Contact Glomo support to enable it. White-labelled checkouts always stay light."]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["On the web SDK, the loading screen starts light and switches once checkout has confirmed dark mode is enabled for your account."]},{"$$mdtype":"Tag","name":"Heading","attributes":{"level":2,"id":"light-and-dark-mean-the-same-thing-everywhere","__idx":2},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["light"]}," and ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["dark"]}," mean the same thing everywhere"]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["If you want a specific scheme, pass ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["light"]}," or ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["dark"]},". Those two values are the portable ones: they mean exactly the same thing on every Glomo SDK, and an integration that drives the property from its own theme state behaves identically across platforms."]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["The automatic value is the one that differs."]},{"$$mdtype":"Tag","name":"Heading","attributes":{"level":2,"id":"what-the-automatic-value-resolves-to","__idx":3},"children":["What the automatic value resolves to"]},{"$$mdtype":"Tag","name":"div","attributes":{"className":"md-table-wrapper"},"children":[{"$$mdtype":"Tag","name":"table","attributes":{"className":"md"},"children":[{"$$mdtype":"Tag","name":"thead","attributes":{},"children":[{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"th","attributes":{"data-label":"SDK"},"children":["SDK"]},{"$$mdtype":"Tag","name":"th","attributes":{"data-label":"Value"},"children":["Value"]},{"$$mdtype":"Tag","name":"th","attributes":{"data-label":"Resolves to"},"children":["Resolves to"]}]}]},{"$$mdtype":"Tag","name":"tbody","attributes":{},"children":[{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/unified-sdk#dark-mode"},"children":["Unified SDK (Web)"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["'system'"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":["The customer's device setting, including changes made while checkout is open."]}]},{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/flutter-sdk/v2#dark-mode"},"children":["Flutter"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["GlomoColorScheme.auto"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["Theme.of(context).brightness"]}," where the checkout is mounted - your app's own appearance, not the device's. An app on ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["ThemeMode.system"]}," therefore gets the device setting, because that is what its theme already reports."]}]},{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/react-native-sdk/v5#dark-mode"},"children":["React Native"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["\"auto\""]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["Appearance.getColorScheme()"]},", which is your app's ",{"$$mdtype":"Tag","name":"em","attributes":{},"children":["effective"]}," appearance. If your app calls ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["Appearance.setColorScheme()"]},", that value is what the SDK sees - React Native overwrites the device value in place and exposes nothing that reports what it overwrote."]}]},{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/ios-sdk/v1#dark-mode"},"children":["iOS"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":[".auto"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":["The checkout's own trait collection, so an app that sets ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["overrideUserInterfaceStyle"]}," gets what it set rather than what the device is on."]}]},{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/android-sdk/v2#dark-mode"},"children":["Android"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["GlomoColorScheme.AUTO"]}]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":["Your app's own appearance, from the most specific source that can answer: ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["AppCompatDelegate.getDefaultNightMode()"]}," if you have set one, otherwise your theme's ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["isLightTheme"]},", otherwise the device configuration."]}]}]}]}]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["Note the web SDK differs twice over: the value is spelled ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["'system'"]}," rather than ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["auto"]},", and it is not the default. Leave ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["appColorScheme"]}," out on the web and checkout stays light. On all four mobile SDKs the automatic value ",{"$$mdtype":"Tag","name":"em","attributes":{},"children":["is"]}," the default, so an integration that sets nothing already follows the host app."]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["The mobile SDKs spell it ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["auto"]}," rather than ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["system"]}," on purpose. On a mobile host the value the SDK can reach is the application's appearance, not the operating system's underlying setting - calling it ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["system"]}," would promise something three of the four platforms cannot deliver."]},{"$$mdtype":"Tag","name":"Heading","attributes":{"level":2,"id":"changing-the-scheme-while-a-checkout-is-open","__idx":4},"children":["Changing the scheme while a checkout is open"]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["Supported on every SDK, and on none of them does it reload the page - the live page is told directly, so a payment in flight survives the change."]},{"$$mdtype":"Tag","name":"div","attributes":{"className":"md-table-wrapper"},"children":[{"$$mdtype":"Tag","name":"table","attributes":{"className":"md"},"children":[{"$$mdtype":"Tag","name":"thead","attributes":{},"children":[{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"th","attributes":{"data-label":"SDK"},"children":["SDK"]},{"$$mdtype":"Tag","name":"th","attributes":{"data-label":"How"},"children":["How"]}]}]},{"$$mdtype":"Tag","name":"tbody","attributes":{},"children":[{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":["Unified SDK (Web)"]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["checkout.setAppColorScheme('dark')"]}]}]},{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":["Flutter"]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":["Pass a new value to the ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["GlomoPayCheckout"]}," widget"]}]},{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":["React Native"]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":["Pass a new value to the ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["GlomoCheckout"]}," component"]}]},{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":["iOS"]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["handle.setAppColorScheme(.dark)"]}," on the handle returned by ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["startCheckout"]}]}]},{"$$mdtype":"Tag","name":"tr","attributes":{},"children":[{"$$mdtype":"Tag","name":"td","attributes":{},"children":["Android"]},{"$$mdtype":"Tag","name":"td","attributes":{},"children":[{"$$mdtype":"Tag","name":"code","attributes":{},"children":["handle.setAppColorScheme(GlomoColorScheme.DARK)"]}," on the handle returned by ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["startCheckout"]}]}]}]}]}]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":[{"$$mdtype":"Tag","name":"strong","attributes":{},"children":["Do not remount, dismiss or restart the checkout to change the scheme."]}," That reloads the WebView and loses the payment. This is the one way to get this wrong that costs something."]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["Two caveats on the mobile SDKs:"]},{"$$mdtype":"Tag","name":"ul","attributes":{},"children":[{"$$mdtype":"Tag","name":"li","attributes":{},"children":["A change that lands while the page is still loading may be missed. The SDK hands it over and does not reload the checkout to force it through, so nothing errors and the payment is never interrupted - the page simply keeps the scheme it started with. For a guaranteed scheme, set ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["appColorScheme"]}," before the checkout opens."]},{"$$mdtype":"Tag","name":"li","attributes":{},"children":["Whether a ",{"$$mdtype":"Tag","name":"em","attributes":{},"children":["device"]}," toggle reaches an open checkout depends on the platform. On iOS and on Android it does, while the scheme is automatic and the host's own appearance follows the device. On Android, a host that has never called ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["AppCompatDelegate.setDefaultNightMode"]}," is resolved from its theme once at launch, so a raw device toggle mid-checkout is not followed; drive it yourself with ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["setAppColorScheme"]}," from your configuration callback if you need it. On React Native the automatic value is read when you call ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["start()"]},"."]}]},{"$$mdtype":"Tag","name":"Heading","attributes":{"level":2,"id":"android-keep-uimode-in-androidconfigchanges","__idx":5},"children":["Android: keep ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["uiMode"]}," in ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["android:configChanges"]}]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["This one is not about ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["appColorScheme"]},", and it is not new - but it matters more now that users have a reason to toggle their theme mid-payment."]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["Your checkout activity needs ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["uiMode"]}," in its ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["android:configChanges"]},":"]},{"$$mdtype":"Tag","name":"CodeBlock","attributes":{"data-language":"xml","header":{"controls":{"copy":{}}},"source":"<activity\n    android:name=\".MainActivity\"\n    android:configChanges=\"keyboard|keyboardHidden|orientation|screenLayout|screenSize|smallestScreenSize|uiMode\">\n","lang":"xml"},"children":[]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["Without it, an OS dark-mode toggle destroys and recreates your activity mid-checkout and loses the payment in flight. Flutter's ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["MainActivity"]}," template already includes it. This applies to the Flutter and React Native SDKs, which render inside your activity; the native Android SDK owns its own activity and declares this itself."]},{"$$mdtype":"Tag","name":"Heading","attributes":{"level":2,"id":"the-names-on-the-wire","__idx":6},"children":["The names on the wire"]},{"$$mdtype":"Tag","name":"p","attributes":{},"children":["The property is ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["appColorScheme"]}," on every SDK. The query parameter the checkout page reads is ",{"$$mdtype":"Tag","name":"code","attributes":{},"children":["colorScheme"]},". The two were not renamed together, so a checkout URL captured from a proxy or a debug log will not match the property name you set. Nothing to configure either way."]},{"$$mdtype":"Tag","name":"Heading","attributes":{"level":2,"id":"related","__idx":7},"children":["Related"]},{"$$mdtype":"Tag","name":"ul","attributes":{},"children":[{"$$mdtype":"Tag","name":"li","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/unified-sdk#dark-mode"},"children":["Unified SDK (Web) - Dark mode"]}]},{"$$mdtype":"Tag","name":"li","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/flutter-sdk/v2"},"children":["Flutter SDK v2"]}]},{"$$mdtype":"Tag","name":"li","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/react-native-sdk/v5"},"children":["React Native SDK v5"]}]},{"$$mdtype":"Tag","name":"li","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/android-sdk/v2"},"children":["Android SDK v2"]}]},{"$$mdtype":"Tag","name":"li","attributes":{},"children":[{"$$mdtype":"Tag","name":"MarkdownLink","attributes":{"href":"/platform/sdk/ios-sdk/v1"},"children":["iOS SDK v1"]}]}]}]},"headings":[{"value":"Dark mode","id":"dark-mode","depth":1},{"value":"It requests a scheme, it does not force one","id":"it-requests-a-scheme-it-does-not-force-one","depth":2},{"value":"light and dark mean the same thing everywhere","id":"light-and-dark-mean-the-same-thing-everywhere","depth":2},{"value":"What the automatic value resolves to","id":"what-the-automatic-value-resolves-to","depth":2},{"value":"Changing the scheme while a checkout is open","id":"changing-the-scheme-while-a-checkout-is-open","depth":2},{"value":"Android: keep uiMode in android:configChanges","id":"android-keep-uimode-in-androidconfigchanges","depth":2},{"value":"The names on the wire","id":"the-names-on-the-wire","depth":2},{"value":"Related","id":"related","depth":2}],"frontmatter":{"title":"Dark mode","seo":{"title":"Dark mode"}},"lastModified":"2026-10-29T14:47:01.000Z","pagePropGetterError":{"message":"","name":""}},"slug":"/platform/sdk/dark-mode","userData":{"isAuthenticated":false,"teams":["anonymous"]},"isPublic":true}