poker-html-client
Version:
HTML client for online poker
456 lines (416 loc) • 16.9 kB
text/typescript
/* tslint:disable:no-bitwise */
declare var apiHost: string;
declare var host: string;
import * as ko from "knockout";
import * as moment from "moment";
import { Game } from "../api/game";
import { LobbyTournamentItem, Tournament } from "../api/tournament";
import { App } from "../app";
import { appConfig } from "../appconfig";
import { debugSettings } from "../debugsettings";
import { _ } from "../languagemanager";
import * as metadataManager from "../metadatamanager";
import { reloadManager } from "../services";
import { tableManager } from "../table/tablemanager";
import * as timeService from "../timeservice";
import { PageBase } from "../ui/pagebase";
declare var app: App;
export class CashOptions {
public currency: KnockoutObservable<number>;
public limits: KnockoutObservable<number>;
public bets: KnockoutObservable<number>;
public maxPlayers: KnockoutObservable<number>;
constructor() {
// require("extenders");
this.currency = ko.observable(2).extend({
options: {
caption: "currency.caption",
items: [
{ text: "currency.realmoney", value: 1 },
{ text: "currency.gamemoney", value: 2 },
],
},
});
this.limits = ko.observable(0).extend({
options: {
caption: "limits.caption",
items: [
{ text: "common.any", value: 0 },
{ text: "limits.limit1", value: 1 },
{ text: "limits.limit2", value: 2 },
{ text: "limits.limit3", value: 3 },
],
},
});
this.bets = ko.observable(0).extend({
options: {
caption: "bets.caption",
items: [
{ text: "common.any", value: 0 },
{ text: "bets.level1", value: 1 << 0 | 1 << 1 | 1 << 2 },
{ text: "bets.level2", value: 1 << 3 | 1 << 4 | 1 << 5 | 1 << 6 },
{ text: "bets.level3", value: 1 << 7 | 1 << 8 | 1 << 9 },
],
},
});
this.maxPlayers = ko.observable(0).extend({
options: {
caption: "players.caption",
items: [
{ text: "common.any", value: 0 },
{ text: "players.players2", value: 2 },
{ text: "players.players6", value: 6 },
{ text: "players.players10", value: 10 },
],
},
});
}
}
export class TournamentOptions {
public currency: KnockoutObservable<number>;
public buyin: KnockoutObservable<number>;
public speed: KnockoutObservable<number>;
public maxPlayers: KnockoutObservable<number>;
constructor() {
// require("extenders");
this.currency = ko.observable(2).extend({
options: {
caption: "currency.caption",
items: [
{ text: "currency.realmoney", value: 1 },
{ text: "currency.gamemoney", value: 2 },
],
},
});
this.buyin = ko.observable(0).extend({
options: {
caption: "buyin.caption",
items: [
{ text: "common.any", value: 0 },
{ text: "buyin.freeroll", value: 1 },
{ text: "buyin.level1", value: 1 << 1 | 1 << 2 | 1 << 3 },
{ text: "buyin.level2", value: 1 << 4 | 1 << 5 | 1 << 6 },
{ text: "buyin.level3", value: 1 << 7 | 1 << 8 | 1 << 9 },
],
},
});
this.speed = ko.observable(0).extend({
options: {
caption: "speed.caption",
items: [
{ text: "common.any", value: 0 },
{ text: "speed.normal", value: 1 },
{ text: "speed.turbo", value: 2 },
{ text: "speed.turbo2x", value: 3 },
],
},
});
this.maxPlayers = ko.observable(0).extend({
options: {
caption: "players.caption",
items: [
{ text: "common.any", value: 0 },
{ text: "players.players2", value: 1 },
{ text: "players.players6", value: 2 },
{ text: "players.players10", value: 3 },
],
},
});
}
}
interface LobbyTournamentItemEx extends LobbyTournamentItem {
duration: string;
}
export class LobbyPage extends PageBase {
public online: KnockoutObservable<string>;
public registered: KnockoutObservable<string>;
public captionLabel: KnockoutComputed<string>;
public slider: Slider;
public cashOptions: CashOptions;
public tournamentOptions: TournamentOptions;
public sngOptions: TournamentOptions;
public showFilterSlider: KnockoutObservable<boolean>;
public showItemsListSlider: KnockoutObservable<boolean>;
public filterLocked: KnockoutObservable<boolean>;
public tournamentsCaption: KnockoutComputed<string>;
public selectionCaption: KnockoutComputed<string>;
public tournaments: KnockoutObservableArray<LobbyTournamentItemEx>;
public sngs: KnockoutObservableArray<LobbyTournamentItemEx>;
public tables: KnockoutObservableArray<any>;
public loading: KnockoutObservable<boolean>;
public currentTime: KnockoutComputed<string>;
constructor() {
super();
const self = this;
App.addTabBarItemMapping("lobby", "tablesFilter");
App.addTabBarItemMapping("lobby", "tournamentsFilter");
App.addTabBarItemMapping("lobby", "sngFilter");
this.currentTime = ko.computed(function () {
return timeService.currentTime();
}, this);
this.online = metadataManager.online;
this.registered = metadataManager.registered;
this.captionLabel = ko.computed(function () {
return _("header.onlinePlayersShort")
.replace("#registered", this.registered())
.replace("#online", this.online());
}, this);
this.tournamentsCaption = ko.computed(function () {
return _("tournamentsList.headerCaption")
.replace("#count", "0".toString());
}, this);
this.cashOptions = new CashOptions();
this.tournamentOptions = new TournamentOptions();
this.sngOptions = new TournamentOptions();
this.tournaments = ko.observableArray<LobbyTournamentItemEx>([]);
this.sngs = ko.observableArray<LobbyTournamentItemEx>([]);
this.tables = ko.observableArray([]);
this.showFilterSlider = ko.observable(false);
this.showItemsListSlider = ko.observable(true);
this.filterLocked = ko.observable(false);
this.slider = new Slider();
this.slider.addOption(_("lobby.cashGames"), "cash", null);
this.slider.addOption(_("lobby.tournaments"), "tournaments", null);
this.slider.addOption(_("lobby.sitAndGo"), "sng", null);
if (!appConfig.tournament.enabled) {
this.slider.enabled(false);
}
this.loading = ko.observable(false);
this.selectionCaption = ko.computed(function () {
if (self.slider.currentIndex() === 0) {
return _("tablesList.headerCaption")
.replace("#count", self.tables().length.toString());
}
if (self.slider.currentIndex() === 1) {
return _("tournamentsList.headerCaption")
.replace("#count", self.tournaments().length.toString());
}
return _("tournamentsList.sngCaption")
.replace("#count", self.sngs().length.toString());
}, this);
tableManager.tables.subscribe(function () {
self.updateOpenedTables();
});
}
public deactivate(pageName?: string) {
super.deactivate(pageName);
// Clear tables and tournaments since this is
// show page faster and it could quicker respond
// to the user input.
this.tables([]);
this.tournaments([]);
this.sngs([]);
}
public activate(pageName?: string) {
if (this.visible()) {
return;
}
const self = this;
this.showFilterSlider(PageBlock.useDoubleView);
this.showItemsListSlider(!PageBlock.useDoubleView);
if (pageName === "lobby") {
this.update(false);
if (!PageBlock.useDoubleView) {
if (ko.contextFor($(".sub-page.filter .swipe")[0]).$swiper) {
ko.contextFor($(".sub-page.filter .swipe")[0]).$swiper.enable(false);
}
}
reloadManager.setReloadCallback(() => self.update(true));
}
super.activate(pageName);
}
public updateOpenedTables() {
const tables = this.tables();
tables.forEach(function (item) {
item.IsOpened = tableManager.isOpened(item.TableId);
});
this.tables([]);
this.tables(tables);
}
public async update(force: boolean) {
if (this.loading() && !force) {
return;
}
const self = this;
metadataManager.updateOnline();
// Added reloading of the all information.
const resetLoading = function () {
self.loading(false);
};
this.loading(true);
try {
await Promise.all([this.refreshTables(), this.refreshTournaments(2), this.refreshTournaments(3)]);
} finally {
resetLoading();
}
}
public showGames() {
if (this.slider.currentIndex() === 0) {
app.lobbyPageBlock.showSecondary("tablesList");
} else {
if (this.slider.currentIndex() === 1) {
app.lobbyPageBlock.tournamentsListPage.setOptions(2, this.tournamentOptions);
app.lobbyPageBlock.showSecondary("tournamentsList");
} else {
app.lobbyPageBlock.sngListPage.setOptions(3, this.sngOptions);
app.lobbyPageBlock.showSecondary("sngList");
}
}
}
public async refreshTables() {
const self = this;
const gameApi = new Game(host);
const privateTables = 0;
const fullTables = null;
const options = this.cashOptions;
const maxPlayers = options.maxPlayers() === 0 ? 0 : 1 << options.maxPlayers();
const betLevels = options.bets();
const moneyType = options.currency();
const limitType = options.limits();
const data = await gameApi.getTables();
if (!self.visible()) {
return;
}
if (data.Status === "Ok") {
self.log("Informaton about tables received: ", data.Data);
const tables = data.Data as any[];
tables.forEach(function (item) {
item.IsOpened = tableManager.isOpened(item.TableId);
});
self.tables(tables);
if (appConfig.auth.automaticTableSelection && tables.length === 1) {
this.selectTable(tables[0]);
}
if (appConfig.game.seatMode || appConfig.game.tablePreviewMode) {
const tableIdString = localStorage.getItem("tableId");
if (tableIdString !== null) {
const tableIdInt = parseInt(tableIdString, 10);
const tableData = await gameApi.getTableById(tableIdInt);
self.selectTable(tableData.Data);
}
}
}
}
public async refreshTournaments(tournamentType) {
const self = this;
const tournamentApi = new Tournament(host);
const options = tournamentType === 2 ? this.tournamentOptions : this.sngOptions;
const prizeCurrency = options.currency();
const tournamentTypeMask = 1 << tournamentType;
const speed = options.speed() === 0 ? 0 : 1 << options.speed();
const buyin = options.buyin();
const maxPlayers = options.maxPlayers() === 0 ? 0 : 1 << (options.maxPlayers() - 1);
const data = await tournamentApi.getTournaments(prizeCurrency, tournamentTypeMask, speed, buyin, maxPlayers);
if (!self.visible()) {
return;
}
if (data.Status === "Ok") {
self.log("Informaton about tournaments received: ", data.Data);
const enchance = (item: LobbyTournamentItem) => {
const result = item as LobbyTournamentItemEx;
const startDate = moment(item.StartDate);
const currentMoment = moment().add(timeService.timeDiff, "ms");
const duration = moment.duration(currentMoment.diff(startDate));
const m = duration.minutes();
result.duration = duration.hours() + _("common.hours")
+ _("common.timeseparator")
+ (m < 10 ? "0" + m : "" + m) + _("common.minutes");
return result;
};
if (tournamentType === 2) {
self.tournaments(data.Data.map(enchance));
} else {
self.sngs(data.Data.map(enchance));
}
}
}
public selectTable(table: GameTableModel) {
app.processing(true);
app.requireGuestAuthentication().then(function (newValue, wasAuthenticated) {
if (newValue) {
app.executeCommand("app.selectTable", [table, wasAuthenticated]);
if (appConfig.game.seatMode || appConfig.game.tablePreviewMode) {
const tableId = table.TableId.toString();
console.log("Save table id " + tableId + " for future auto select of this table.");
localStorage.setItem("tableId", tableId);
}
if (appConfig.game.seatMode) {
app.executeCommand("page.seats");
} else {
app.executeCommand("page.tables");
}
app.processing(false);
} else {
app.processing(false);
}
});
}
public selectTournament(tournament) {
app.lobbyPageBlock.selectTournament(tournament);
}
public showFilterOptions() {
if (this.slider.currentIndex() === 0) {
app.lobbyPageBlock.showSecondary("filter");
}
if (this.slider.currentIndex() === 1) {
app.lobbyPageBlock.showSecondary("filter");
}
if (this.slider.currentIndex() === 2) {
app.lobbyPageBlock.showSecondary("filter");
}
}
public showLobby() {
if (this.slider.currentIndex() === 0) {
app.lobbyPageBlock.showSecondary("lobby");
}
if (this.slider.currentIndex() === 1) {
app.lobbyPageBlock.showSecondary("lobby");
}
if (this.slider.currentIndex() === 2) {
app.lobbyPageBlock.showSecondary("lobby");
}
}
public selectFilterParameter(parameter, value) {
parameter(value);
if (PageBlock.useDoubleView) {
app.lobbyPageBlock.showSecondary("lobby");
}
}
public async refresh() {
metadataManager.updateOnline();
if (this.slider.currentIndex() === 0) {
this.loading(true);
try {
await this.refreshTables();
} finally {
this.loading(false);
}
}
if (this.slider.currentIndex() === 1) {
this.loading(true);
try {
await this.refreshTournaments(2);
} finally {
this.loading(false);
}
}
if (this.slider.currentIndex() === 2) {
this.loading(true);
try {
await this.refreshTournaments(3);
} finally {
this.loading(false);
}
}
}
public touchLock(e: Event) {
if (this.filterLocked()) {
e.preventDefault();
}
}
private log(message: string, ...params: any[]) {
if (debugSettings.lobby.trace) {
console.log(message, params);
}
}
}