mirror of
https://github.com/tobspr/shapez.io.git
synced 2025-06-13 13:04:03 +00:00
190 lines
6.4 KiB
JavaScript
190 lines
6.4 KiB
JavaScript
/* typehints:start */
|
|
import { Application } from "../../application";
|
|
/* typehints:end */
|
|
|
|
import { AdProviderInterface } from "../ad_provider";
|
|
import { createLogger } from "../../core/logging";
|
|
import { ClickDetector } from "../../core/click_detector";
|
|
import { performanceNow } from "../../core/builtins";
|
|
import { clamp } from "../../core/utils";
|
|
import { T } from "../../translations";
|
|
|
|
const logger = createLogger("adprovider/adinplay");
|
|
|
|
const minimumTimeBetweenVideoAdsMs = G_IS_DEV ? 1 : 15 * 60 * 1000;
|
|
|
|
export class AdinplayAdProvider extends AdProviderInterface {
|
|
/**
|
|
*
|
|
* @param {Application} app
|
|
*/
|
|
constructor(app) {
|
|
super(app);
|
|
|
|
/** @type {ClickDetector} */
|
|
this.getOnSteamClickDetector = null;
|
|
|
|
/** @type {Element} */
|
|
this.adContainerMainElement = null;
|
|
|
|
/**
|
|
* The resolve function to finish the current video ad. Null if none is currently running
|
|
* @type {Function}
|
|
*/
|
|
this.videoAdResolveFunction = null;
|
|
|
|
/**
|
|
* The current timer which will timeout the resolve
|
|
*/
|
|
this.videoAdResolveTimer = null;
|
|
|
|
/**
|
|
* When we showed the last video ad
|
|
*/
|
|
this.lastVideoAdShowTime = -1e20;
|
|
}
|
|
|
|
getHasAds() {
|
|
return true;
|
|
}
|
|
|
|
getCanShowVideoAd() {
|
|
return (
|
|
this.getHasAds() &&
|
|
!this.videoAdResolveFunction &&
|
|
performanceNow() - this.lastVideoAdShowTime > minimumTimeBetweenVideoAdsMs
|
|
);
|
|
}
|
|
|
|
initialize() {
|
|
// No point to initialize everything if ads are not supported
|
|
if (!this.getHasAds()) {
|
|
return Promise.resolve();
|
|
}
|
|
|
|
logger.log("🎬 Initializing Adinplay");
|
|
|
|
// Add the preroll element
|
|
this.adContainerMainElement = document.createElement("div");
|
|
this.adContainerMainElement.id = "adinplayVideoContainer";
|
|
this.adContainerMainElement.innerHTML = `
|
|
<div class="adInner">
|
|
<div class="videoInner">
|
|
|
|
</div>
|
|
</div>
|
|
`;
|
|
|
|
// Add the setup script
|
|
const setupScript = document.createElement("script");
|
|
setupScript.textContent = `
|
|
var aiptag = aiptag || {};
|
|
aiptag.cmd = aiptag.cmd || [];
|
|
aiptag.cmd.display = aiptag.cmd.display || [];
|
|
aiptag.cmd.player = aiptag.cmd.player || [];
|
|
`;
|
|
document.head.appendChild(setupScript);
|
|
|
|
window.aiptag.gdprShowConsentTool = 0;
|
|
window.aiptag.gdprAlternativeConsentTool = 1;
|
|
window.aiptag.gdprConsent = 1;
|
|
|
|
const scale = this.app.getEffectiveUiScale();
|
|
const targetW = 960;
|
|
const targetH = 540;
|
|
|
|
const maxScaleX = (window.innerWidth - 100 * scale) / targetW;
|
|
const maxScaleY = (window.innerHeight - 150 * scale) / targetH;
|
|
|
|
const scaleFactor = clamp(Math.min(maxScaleX, maxScaleY), 0.25, 2);
|
|
|
|
const w = Math.round(targetW * scaleFactor);
|
|
const h = Math.round(targetH * scaleFactor);
|
|
|
|
// Add the player
|
|
const videoElement = this.adContainerMainElement.querySelector(".videoInner");
|
|
this.adContainerMainElement.querySelector(".adInner").style.maxWidth = w + "px";
|
|
|
|
const self = this;
|
|
window.aiptag.cmd.player.push(function () {
|
|
window.adPlayer = new window.aipPlayer({
|
|
AD_WIDTH: w,
|
|
AD_HEIGHT: h,
|
|
AD_FULLSCREEN: false,
|
|
AD_CENTERPLAYER: false,
|
|
LOADING_TEXT: T.global.loading,
|
|
PREROLL_ELEM: function () {
|
|
return videoElement;
|
|
},
|
|
AIP_COMPLETE: function () {
|
|
logger.log("🎬 ADINPLAY AD: completed");
|
|
self.adContainerMainElement.classList.add("waitingForFinish");
|
|
},
|
|
AIP_REMOVE: function () {
|
|
logger.log("🎬 ADINPLAY AD: remove");
|
|
if (self.videoAdResolveFunction) {
|
|
self.videoAdResolveFunction();
|
|
}
|
|
},
|
|
});
|
|
});
|
|
|
|
// Load the ads
|
|
const aipScript = document.createElement("script");
|
|
aipScript.src = "https://api.adinplay.com/libs/aiptag/pub/YRG/shapez.io/tag.min.js";
|
|
aipScript.setAttribute("async", "");
|
|
document.head.appendChild(aipScript);
|
|
|
|
return Promise.resolve();
|
|
}
|
|
|
|
showVideoAd() {
|
|
assert(this.getHasAds(), "Called showVideoAd but ads are not supported!");
|
|
assert(!this.videoAdResolveFunction, "Video ad still running, can not show again!");
|
|
this.lastVideoAdShowTime = performanceNow();
|
|
document.body.appendChild(this.adContainerMainElement);
|
|
this.adContainerMainElement.classList.add("visible");
|
|
this.adContainerMainElement.classList.remove("waitingForFinish");
|
|
|
|
try {
|
|
// @ts-ignore
|
|
window.aiptag.cmd.player.push(function () {
|
|
console.log("🎬 ADINPLAY AD: Start pre roll");
|
|
window.adPlayer.startPreRoll();
|
|
});
|
|
} catch (ex) {
|
|
logger.warn("🎬 Failed to play video ad:", ex);
|
|
document.body.removeChild(this.adContainerMainElement);
|
|
this.adContainerMainElement.classList.remove("visible");
|
|
return Promise.resolve();
|
|
}
|
|
|
|
return new Promise(resolve => {
|
|
// So, wait for the remove call but also remove after N seconds
|
|
this.videoAdResolveFunction = () => {
|
|
this.videoAdResolveFunction = null;
|
|
clearTimeout(this.videoAdResolveTimer);
|
|
this.videoAdResolveTimer = null;
|
|
|
|
// When the ad closed, also set the time
|
|
this.lastVideoAdShowTime = performanceNow();
|
|
resolve();
|
|
};
|
|
|
|
this.videoAdResolveTimer = setTimeout(() => {
|
|
logger.warn(this, "Automatically closing ad after not receiving callback");
|
|
if (this.videoAdResolveFunction) {
|
|
this.videoAdResolveFunction();
|
|
}
|
|
}, 120 * 1000);
|
|
})
|
|
.catch(err => {
|
|
logger.error("Error while resolving video ad:", err);
|
|
})
|
|
.then(() => {
|
|
document.body.removeChild(this.adContainerMainElement);
|
|
this.adContainerMainElement.classList.remove("visible");
|
|
});
|
|
}
|
|
}
|