How to show ADS in my App?

Previous topic - Next topic

msx

I tried to follow this thread to show ADS in my application but I can not not show anything and if I look admod reports also shows requests. I do not know that I can be doing wrong. Still it works?

spacefractal

Recently im actuelly have dropped support for Google Ads, because its have prove its was crashing on some devices. Inapp Purchase is still possible. Mr Plow do have code seen as a coder :-).

Also Google Service jar version might have been updated, make sure the version number is correct in the androidmanifest.xml.

Also if there is some issues, its often output to logcat.
Genius.Greedy Mouse - Karma Miwa - Spot Race - CatchOut - PowerUp Elevation - The beagle Jam - Cave Heroes 2023 - https://spacefractal.itch.io/

msx

where I could find the code for IAP?. I find nothing in the forum.

MrPlow

#3
Quote from: msx on 2016-Jul-18
where I could find the code for IAP?. I find nothing in the forum.

Hi There

Here is the inapp_functions.gbas and inapp_config.gbas files I use for Android.

Code (glbasic) Select
// --------------------------------- //
// Project: Project Glbasic StoreKit
//
// Copyright (C) 2013 Alan Bostrup AKA Space Fractal.
//
// Licensed under the Apache License, Version 2.0 (the "License"). You may
// obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
// Unless required by applicable law OR agreed TO IN writing, software distributed
// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
// CONDITIONS OF ANY KIND, either express OR implied. See the License FOR the
// specific language governing permissions AND limitations under the License.
//¨
// This is version v1.0
//                      Beta 5 - Cleaned up Google Play and OUYA key comment. no code changed.
//                      Beta 4 - Splitted config and functions to each ther file
//                               and more fixes to the
//                      Beta 3 - few key issues fixed in InAppHelper_Init()
//                               more comments about some of the functions to
//                               advoid confuctions.
//                      Beta 2 - Added OUYA Support
//                      Beta 1 - MkStoreKit Support (iOS)
//
// ANDROID EXTRAS is required for Android veresion, new and links can been found here:
// http://www.glbasic.com/forum/index.php?topic=9644.0
//
// You also need to add Funcs_General.gbas, hashnumber.gbas and AndroidExtras.gbas to your project.
//
// Please Note, until all stores is ready, only none-consumable would been
// supported.

GLOBAL INAPP_ERROR$=""      // When a error in a purchase or when restoring.
GLOBAL INAPP_ISONLINE=0     // is network on?
GLOBAL INAPP_PURCHASE$=""   // when a purchase just have been succed.
GLOBAL INAPP_ACTIVATE$=""   // a user is doing the order progress (chould should "progress" to user, if INAPP_ACTIVATE have any content).
GLOBAL INAPP_STATUS$=""     // wating for a callback for either retore or purchase (this can been used when pause was activated).

// Functions that can been used:
// - InAppPurchase_isOnline() <- IS store online (might not work on all shops).
// - InAppPurchase_Price$("general SKU name") <- Get a price of a SKU.
// - InAppPurchase_isAvailable("general SKU name") <- This return a HASH value, NOT 0 or 1, but two other values based on the Windows key (you can set it here).
// - InAppPurchase_Activate("general SKU name")   <- This start the inapp purchase progress.
// - InAppPurchase_Restore() <- This is REQURIED for Apple AppStore.
// - InAppPurchase_Update() <- uses this in the main loop after SHOWSCREEN and before loading.


// **************************** INAPP SHOP FUNCTIONS START HERE ****************************
GLOBAL INAPP_INIT=0
GLOBAL INAPP_ERROR_TIMER=0  // time before error message vanish.
GLOBAL INAPP_STORE$=""      // the store name going to been used.
GLOBAL INAPP_PURCHASES$=""  // a recent purchase, but waiting for receipt (ANDROID ONLY)
GLOBAL INAPP_RECEPTOK = 0   // Have recept to been checked (ANDROID ONLY)

?IFDEF IPHONE
IMPORT "C" int StoreIsOnline(int) // parents check if the inapp is disabled (0=init once, 1=reinit again).
IMPORT "C" int StoreIsFeaturePurchased(const char*, int) // checks if the feature have been purchased
IMPORT "C" int StoreRestored() // is store have been complete (1) or failed (-1)?
IMPORT "C" void StoreRestore() // Restore any previous purchased items (required on iOS).
IMPORT "C" int StoreActivate(const char*) // User have just pressed on the buys button in your app.
IMPORT "C" const char* StoreGetPrice(const char*) // Get a Price for the product.
IMPORT "C" int StoreActivated() // check the purchasing item....
?ENDIF


// is the store online?
FUNCTION InAppPurchase_isOnline:
// DEPRINT("InAppPurchase_isOnline()")
?IFDEF IPHONE
LOCAL ok=StoreIsOnline(0)
RETURN ok
?ENDIF

?IFDEF ANDROID
IF INAPP_STORE$=""
INAPP_STORE$=JavaCall$("Shop:GetAppStoreName")
DEPRINT("Store Connected: "+INAPP_STORE$)
IF INAPP_STORE$="-1" OR INAPP_STORE$="no"
INAPP_STORE$=""
ENDIF
IF LEN(INAPP_STORE$)<3 THEN INAPP_STORE$=""
IF INAPP_STORE$="" THEN RETURN 0
RETURN 1
ENDIF
?ENDIF
ENDFUNCTION

// get a price of the current product
FUNCTION InAppPurchase_Price$: iID$
STATIC IDDD$
STATIC IDPRICE$
STATIC counter=0


iID$=InAppConfig_SkuNames$(iID$, INAPP_STORE$)

?IFDEF WIN32
RETURN "Free"
?ENDIF

?IFDEF IPHONE
IF IDDD$=iID$ AND IDPRICE$<>"unknown" THEN RETURN IDPRICE$
LOCAL price$=StoreGetPrice(iID$)
price$=TRIM$(price$)
IDDD$=iID$
IDPRICE$=price$
RETURN price$
?ENDIF

?IFDEF ANDROID
IF IDDD$=iID$ AND IDPRICE$<>"unknown" THEN RETURN IDPRICE$
LOCAL price$=JavaCall$("Shop:GetPrice:"+iID$)
IF price$="" THEN price$="unknown"
IDPRICE$=price$
RETURN price$
?ENDIF
ENDFUNCTION

// is the inapp item available? Etc have you brought the item (1) or not (0)? (consumable is not supported yet)
// for some secure reasons, true and false is easy to been hacked, then its uses some hash to get a bit harder to crach.
//
// to also prevent tapping source for exeample from java, checkout fake products and make sure is returned false, which
// give a constant hash number for that. This could been done in various places in your app.
FUNCTION InAppPurchase_isAvailable: iID$
IF INAPP_STORE$=""
LOCAL ok=JavaCall$("Shop:GetAppStoreName")
IF ok=0 THEN RETURN
ENDIF
DEPRINT("InAppPurchase_isAvailable()"+iID$)
LOCAL orig$=iID$
LOCAL ok%=0
IF INAPP_DEVKEY=0 THEN RETURN 0
orig$=InAppConfig_SkuNames$(iID$, "general")
iID$=InAppConfig_Sku2Names$(iID$, INAPP_STORE$)

?IFDEF WIN32
ok=StoreWin(iID$, INAPP_DEVKEY)
?ENDIF

?IFDEF IPHONE
ok=StoreIsFeaturePurchased(iID$, INAPP_DEVKEY)
?ENDIF

?IFDEF ANDROID
ok=JavaCall$("Shop:isAvailable:"+iID$+":"+INAPP_DEVKEY)
?ENDIF

ok=HashNumberBig(ok)
ok=ok-ABS(HashNumberBig("microsoft.window"))
ok=ok*HashNumber(-ok)
ok=ASL(ok, 4)
ok=ok*HashNumber(orig$)
ok=ok-HashNumber(INAPP_DEVKEY)
ok=ABS(ok)
RETURN ok-1
ENDFUNCTION

?IFDEF WIN32
FUNCTION StoreWin: iID$, keys
// IF INAPP_DEVKEY=0 THEN InAppConfig_PublicKeys$("microsoft.windows")
// IF INAPP_DEVKEY=0 THEN RETURN 0
// LOCAL ok=GetStr$(InAppHelper_HashID$(iID$), "Purchases")
// IF ok=1 THEN RETURN keys
ENDFUNCTION
?ENDIF

// Start the payment progress (etc you have pressed on a purchase button).
// On windows, the purchase is allways succes. On iOS and Android, a
// GLB_ON_PAUSE/() can been called here, so you might checks INAPP_STATUS$ for
// eventuelly checks if there us a purchase ongoing or not in there.
FUNCTION InAppPurchase_Activate: iID$
DEPRINT("InAppPurchase_Activate: "+iID$)
IF INAPP_ERROR$<>"" THEN DEPRINT("error: "+INAPP_ERROR$)
IF INAPP_ACTIVATE$<>"" THEN DEPRINT("allready in progress")
IF INAPP_ERROR$<>"" THEN RETURN FALSE
IF INAPP_ACTIVATE$<>"" THEN RETURN FALSE
IF INAPP_STATUS$<>""
INAPP_ERROR$="allready in progress"
RETURN
ENDIF
iID$=InAppConfig_Sku2Names$(iID$, INAPP_STORE$)
?IFDEF WIN32
InAppPurchase_Finished(iID$)
RETURN TRUE
?ENDIF
?IFDEF IPHONE
StoreActivate(iID$)
INAPP_STATUS$="Activate"
INAPP_ACTIVATE$=iID$
RETURN TRUE
?ENDIF

?IFDEF ANDROID
DEPRINT("InAppPurchase_Activate()")
IF INAPP_STATUS$=""
DEPRINT(iID$)
JavaCall$("Shop:Activate:"+iID$)
INAPP_STATUS$="Activate"
INAPP_ACTIVATE$=iID$
ENDIF
?ENDIF
ENDFUNCTION

// A Purchase have just been activated and then its should been saved here locally.
// Only required for Windows for Fake purchases to save the purchases. Its doing
// automatic on Android as well iOS.
FUNCTION InAppPurchase_Finished: iID$
INAPP_PURCHASE$=iID$
iID$=InAppConfig_Sku2Names$(iID$, INAPP_STORE$)
?IFDEF Win32
SetStr(InAppHelper_HashID$(iID$), "Purchases", 1)
?ENDIF
ENDFUNCTION

// you must do a restore feature for IOS to keep Apple happy to recover all
// perlament purchased items. Dont forget to check the features is Available
// trought InAppPurchase_isAvailable(), which is not automatic done.
//
// a succes would sent a INAPP_PURCHASE$="restored". If user failed to restore
// then a error would been sent to INAPP_ERROR$
//
// This is done automatic on Android and OUYA on startup, but this is required
// for iOS.
FUNCTION InAppPurchase_Restore:
IF INAPP_STATUS$<>"" THEN RETURN

?IFDEF WIN32
FOR i=0 TO 100
LOCAL iID$=InAppConfig_Sku2Names$(i, INAPP_STORE$)
IF iID$<>""
InAppPurchase_Activate(iID$)
ELSE
RETURN
ENDIF
NEXT
?ENDIF

?IFDEF IPHONE
StoreRestore()
INAPP_STATUS$="Restore"
INAPP_ERROR_TIMER=0
?ENDIF
ENDFUNCTION

// This is a updater function, which is required to been invoked in loop time.
// This function checkout ongoing purchases using callbacks. that why you need
// this around a SHOWSCREEN.
FUNCTION InAppPurchase_Update:
LOCAL ok=0
?IFDEF ANDROID
IF INAPP_RECEPTOK=1
INAPP_RECEPTOK=2
INAPP_ERROR$=""
ENDIF
?ENDIF

IF INAPP_ERROR$<>""
INAPP_ERROR_TIMER=INAPP_ERROR_TIMER+1
IF INAPP_ERROR_TIMER>60
INAPP_ERROR_TIMER=0
IF INAPP_ERROR$="success"
INAPP_ERROR$="ok"
ELSE
INAPP_ERROR$=""
ENDIF
ENDIF
ENDIF

?IFDEF WIN32
IF INAPP_INIT=0
INAPP_INIT=1
INAPP_STORE$="microsoft.windows"
ENDIF
?ENDIF

?IFDEF IPHONE
INAPP_STORE$="apple.appstore.ios"
IF INAPP_INIT=0
INAPP_INIT=1
INAPP_ISONLINE=StoreIsOnline(0)
ENDIF

IF INAPP_STATUS$="Activate"
INAPP_ERROR_TIMER=0
ok=StoreActivated()
IF ok=1
INAPP_PURCHASE$=INAPP_ACTIVATE$
INAPP_STATUS$=""
INAPP_ACTIVATE$=""
ELSEIF ok=-1 OR (InAppPurchase_isOnline()=0)
INAPP_STATUS$=""
INAPP_ACTIVATE$=""
INAPP_ERROR$="cancelled or failed"
INAPP_ERROR_TIMER=0
ENDIF
ENDIF

IF INAPP_STATUS$="Restore"
ok=StoreRestored()
IF ok=1
INAPP_RECEPTOK=2
INAPP_PURCHASE$="restored"
INAPP_STATUS$=""
ELSEIF ok=-1
INAPP_ERROR$="failed"
INAPP_STATUS$=""
INAPP_ERROR_TIMER=0
ENDIF
ENDIF
?ENDIF

?IFDEF ANDROID
IF INAPP_INIT=0
INAPP_INIT=1
InAppHelper_Init()
ENDIF

IF LEN(INAPP_STORE$)<3
DEPRINT("update inappstorename")
InAppPurchase_isOnline()
ENDIF

IF INAPP_RECEPTOK<1
ok=JavaCall$("Shop:isReceiptDone")
IF ok=1
INAPP_RECEPTOK=1
INAPP_PURCHASE$="restored"
IF INAPP_PURCHASES$<>""
INAPP_PURCHASE$=INAPP_PURCHASES$
INAPP_PURCHASES$=""
INAPP_STATUS$=""
INAPP_ACTIVATE$=""
ENDIF
ENDIF
ENDIF

IF INAPP_STATUS$="Activate"
INAPP_ERROR_TIMER=0
LOCAL result$=JavaCall$("Shop:Activated")
//DEPRINT("Check Purchase: "+result$)
IF LEFT$(result$, 4)="fail" THEN ok=-1
IF LEFT$(result$, 4)="succ" THEN ok=1
LOCAL isOnline=InAppPurchase_isOnline()
IF ok=1
JavaCall$("Shop:ActivateReset")
INAPP_RECEPTOK=0;
INAPP_PURCHASES$=StringField$(result$, 3, ":")
ELSEIF ok=-1 OR isOnline=0
JavaCall$("Shop:ActivateReset")
INAPP_STATUS$=""
INAPP_ACTIVATE$=""
INAPP_ERROR$="cancelled or failed"
INAPP_ERROR_TIMER=0
ENDIF
ENDIF

?ENDIF
ENDFUNCTION
// **************************** INAPP SHOP FUNCTIONS ENDS HERE ****************************

// *** HELPER FUNCTIONS ****
FUNCTION InAppHelper_SetSku: shop$, i
LOCAL sku$=InAppConfig_Sku2Names$(i, shop$)
LOCAL sgeneral$=InAppConfig_Sku2Names$(i, "general")
IF sku$<>"" AND sku$<>sgeneral$ AND sku$<>"0"
JavaCall$("Shop:SetSku:"+sgeneral$+":"+shop$+":"+sku$)
ENDIF
ENDFUNCTION

FUNCTION InAppHelper_Init: OUYA=0
?IFDEF ANDROID
// items for the store.
JavaCall$("Shop:noItems:"+INAPP_NR_OF_ITEMS)

IF OUYA=0
FOR i=0 TO INAPP_NR_OF_ITEMS-1
JavaCall$("Shop:SetSku:android:"+InAppConfig_Sku2Names$(i, "general")+":"+InAppConfig_Sku2Names$(i, "general"))
InAppHelper_SetSku("com.google.play", i)
InAppHelper_SetSku("com.ouya.shop", i)
InAppHelper_SetSku("com.amazon.apps", i)
InAppHelper_SetSku("com.samsung.apps", i)
InAppHelper_SetSku("com.yandex.store", i)
InAppHelper_SetSku("com.nokia.nstore", i)
InAppHelper_SetSku("Appland", i)
InAppHelper_SetSku("SlideME", i)
InAppHelper_SetSku("cm.aptoide.pt", i)
NEXT
ELSE
FOR i=0 TO INAPP_NR_OF_ITEMS-1
JavaCall$("Shop:SetSku:android:"+InAppConfig_Sku2Names$(i, "general")+":"+InAppConfig_Sku2Names$(i, "general"))
InAppHelper_SetSku("com.ouya.shop", i)
NEXT
ENDIF
JavaCall$("Shop:Init")
?ENDIF
ENDFUNCTION


FUNCTION InAppConfig_Sku2Names$: iID$, store$
RETURN InAppConfig_SkuNames$(iID$, store$)
ENDFUNCTION

// hash an item to save locally when a purchase have been succed.
FUNCTION InAppHelper_HashID$: iID$
LOCAL DID$=PLATFORMINFO$("ID")+iID$
//DEPRINT("InApp_HashID$(): "+DID$)
DID$=ENCRYPT$(DID$, LEFT$(DID$, 5))
DID$=HashNumber(DID$)+""+HashNumber(PLATFORMINFO$("ID"))+""+HashNumber(iID$)+""+472111122
RETURN DID$
ENDFUNCTION


Code (glbasic) Select
// --------------------------------- //
// Project: Project Glbasic StoreKit
//
// Copyright (C) 2013 Alan Bostrup AKA Space Fractal.
//
// Licensed under the Apache License, Version 2.0 (the "License"). You may
// obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
// Unless required by applicable law OR agreed TO IN writing, software distributed
// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
// CONDITIONS OF ANY KIND, either express OR implied. See the License FOR the
// specific language governing permissions AND limitations under the License.
//
//
// This is the variables as well functions that should been changed for the SKU
// setup.

// Please Note:
// Some PERMISSIONS for androidmanifest.xml might been required. For Me (Space Fractal),
// im uses those:
//  <uses-permission android:name="android.permission.INTERNET" />
//  <uses-permission android:name="android.permission.VIBRATE" />
//  <uses-permission android:name="android.permission.BATTERY_STATS" />
//  <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
//  <uses-permission android:name="android.permission.WAKE_LOCK" />
//  <uses-permission android:name="android.permission.BLUETOOTH" />
//  <uses-permission android:name="com.android.vending.BILLING" />


// **************************** CONFIGURATIONS START HERE ****************************
GLOBAL INAPP_NR_OF_ITEMS=1   // numbers of inapp items you want to uses (this is due init to Android). Not needed for iOS.
GLOBAL INAPP_DEVKEY = 123456// just put a totally random sucure key for the hash number (this using for other systems as well).


// InAppConfig_SkuNames$ configuration for various Appstores. In the game, you might want to only
// use one SKU, which is why its need to been find and convert the ID to the correct name
// for the shop. Also ID numbers is also required for init ITEMS for Android.
//
// For iOS, you also need configuere the Sku Names in the MKStoreKitConfigs.plist too. That
// can been done using xCode. They should named the same with the SKU you configuried in the
// iTunes Connect and similar interfaces.
//
// This can take some time to setup that one.
//
// SKUS should not confict each other on Android stores, or OpenIAP might fails to find the correct sku, that even on OUYA.
// If invaild SKU is happens, then you have some SKU or KEYS done wrong. See the Logcat for that (_logview.bat in glbasic folder)
FUNCTION InAppConfig_SkuNames$: iID$, store$
// check name for "The Premium Key"
IF iID$="0" OR iID$="thepremium" // this might not been required for your game with multiply names. numbers ID is requireed too.
IF store$="general"            THEN RETURN "com.gazz.myid"  // This is the shared name for all platforms, can been used as ingame item
IF store$="apple.appstore.ios" THEN RETURN ""  // SKU name for Apple iOS, that one you set in the plist and in Itunes Connect.
IF store$="com.ouya.shop"      THEN RETURN ""  // the SKU name for the OUYA Store.
IF store$="com.google.play"    THEN RETURN "com.gazz.myid  // the SKU name for Google Play.
IF store$="microsoft.windows"  THEN RETURN ""  // SKU name for windows (internal, you should save it locally, not done here).
IF store$="com.samsung.apps"   THEN RETURN ""  // The Inapp Item Number
ENDIF

RETURN iID$
ENDFUNCTION

// The Public key from YOUR APPLICATION'S PUBLIC KEY, you get from the Dev Console for that store.
// those Security keys os fpr Android only and is not needed for iOS.
FUNCTION InAppConfig_PublicKeys$: store$
// do NOT change the store order. If you dop that, then the keys would been sent to a wrong shop and hence its will refuse to work.
IF store$="com.google.play" OR store$=1 THEN RETURN "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCg" // the APPLICATION PUBLIC KEY From Google Play console (a very long string).
IF store$="com.amazon.apps" OR store$=2 THEN RETURN "no.com.amazon.apps"     // not supported IN this version
IF store$="com.tmobile.store" OR store$=3 THEN RETURN "no.com.tmobile.store" // not supported in this version
IF store$="com.samsung.apps" OR store$=4 THEN RETURN "no.com.samsung.apps"   // The Group Item Number
IF store$="com.ouya.shop" OR store$=5 THEN RETURN "THE DEVELOPER KEY"        // the devkey from OUYA Portal. The required application signed key.der is placed in assests/Android/key.der
IF store$="microsoft.windows" THEN RETURN "microsoft.window"                 // you set a another random key, which is used for hash for other stores.
ENDFUNCTION


In your game loop you need to run

InAppPurchase_Update()

every loop

You can check for the purchase during game with

InAppPurchase_isAvailable("com.gazz.myid") // using ur own purchase id relating to your app

To start a purchase...

InAppPurchase_Activate("com.gazz.myid")

-----

Note: Make sure you have good working GLB_ON_PAUSE / GLB_ON_RESUME functions too.

So you need to test you purchase with a device that can buy the IAP.
Then print the code from InAppPurchase_isAvailable("com.gazz.myid") and use that code in your app to create a condition to check if bought or not.

Hope this all makes sense...I am using GLB v12 and old version of AE.








Comp:
Speccy-48k, Speccy-128k, Amigas, PCs

msx

Thank you Mr. Plow. For now I am not very clear what the process. I will try to integrate it into my application and see if I have luck and everything works fine.

MrPlow

I think inapp functions haven't been changed much in versions of AE but Spacefractal would know more about that...

Comp:
Speccy-48k, Speccy-128k, Amigas, PCs

spacefractal

im do thinks there might did a few changes in the techinical side for inapp purchase. Im did updated the storekit somewhere last year to to avoud google inapp purchase v2.0 which got phased out.

Im also thinks OUYA is the best test platform for testing inapp purchases, because google play requires few google accounts to get it work, which can been a quite confuction.
Genius.Greedy Mouse - Karma Miwa - Spot Race - CatchOut - PowerUp Elevation - The beagle Jam - Cave Heroes 2023 - https://spacefractal.itch.io/

MrPlow

I switched to version 2.0 of inapp at the time so the code above should be okay for that...
Comp:
Speccy-48k, Speccy-128k, Amigas, PCs

spacefractal

There is some changes im remember, where im moved all public security keys to strings.xml and not in glbasic, because its was hard to meanstream it, after the new StoreKey update, where google phased out v2 purchase system, and the init was required to been done in OnCreate now, which is invoked before any glbasic code started. SKU was still can do in the inapp_config.gbas throught.

But the idea and functions is pretty much the same, and actuelly im did newer do a real example of this system. Im thinks one of your guys, should do a proper example in the default android example to show off how those works?

Howover im will see can do in the follow weeks to create a inapp purchase example and doing that in the normal android extras example.... There was as im wrote few updates, but only how the public keys is implemented, not the functions its self.

PS. Im do no longer support Google Ads, so im can no longer help on that one. The reason behind, Google Ads have been shown unstablilty and have a lots of malware for its users. Also im also seen, while its works nicely here, its can crash on other devices. So its was a hit or miss.... And, its diddent work on Android TV at all. So im will then focus to doing a better inapp purchase example. But a release might first do after my vaccation, so some where in Aug first.
Genius.Greedy Mouse - Karma Miwa - Spot Race - CatchOut - PowerUp Elevation - The beagle Jam - Cave Heroes 2023 - https://spacefractal.itch.io/