Save all changes
This commit is contained in:
commit
62acb50d14
609 changed files with 96974 additions and 0 deletions
18
.editorconfig
Normal file
18
.editorconfig
Normal file
|
@ -0,0 +1,18 @@
|
|||
root = true
|
||||
|
||||
[*]
|
||||
charset = utf-8
|
||||
end_of_line = LF
|
||||
insert_final_newline = true
|
||||
trim_trailing_whitespace = true
|
||||
indent_style = space
|
||||
indent_size = 2
|
||||
max_line_length = 80
|
||||
|
||||
[*.php]
|
||||
# settings required by PSR-12 standard
|
||||
indent_size = 4
|
||||
max_line_length = 120
|
||||
|
||||
[Makefile]
|
||||
indent_style = tab
|
6
.editorconfig-checker.json
Normal file
6
.editorconfig-checker.json
Normal file
|
@ -0,0 +1,6 @@
|
|||
{
|
||||
"Exclude": [
|
||||
"^.git/",
|
||||
"^.idea/"
|
||||
]
|
||||
}
|
6
2013/daemon/.bzrignore
Normal file
6
2013/daemon/.bzrignore
Normal file
|
@ -0,0 +1,6 @@
|
|||
./cfg/*
|
||||
./log/*
|
||||
./tmp/*
|
||||
./lib/PHPTAL*
|
||||
./public/google*
|
||||
./public/scyzoryk/.htaccess
|
17
2013/daemon/.editorconfig
Normal file
17
2013/daemon/.editorconfig
Normal file
|
@ -0,0 +1,17 @@
|
|||
[*]
|
||||
indent_style = tab
|
||||
max_line_length = unset
|
||||
|
||||
[*.css]
|
||||
max_line_length = 140
|
||||
|
||||
[*.js] # minified files
|
||||
insert_final_newline = unset
|
||||
|
||||
[*.sql]
|
||||
indent_style = space
|
||||
|
||||
[lib/jsmin.php] # vendored file
|
||||
insert_final_newline = unset
|
||||
indent_style = space
|
||||
indent_size = 2
|
20
2013/daemon/LICENSE
Normal file
20
2013/daemon/LICENSE
Normal file
|
@ -0,0 +1,20 @@
|
|||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2013 Krzysztof Sikorski
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
this software and associated documentation files (the "Software"), to deal in
|
||||
the Software without restriction, including without limitation the rights to
|
||||
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
||||
the Software, and to permit persons to whom the Software is furnished to do so,
|
||||
subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
||||
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
||||
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
|
||||
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
||||
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
68
2013/daemon/README.md
Normal file
68
2013/daemon/README.md
Normal file
|
@ -0,0 +1,68 @@
|
|||
INTRODUCTION
|
||||
===
|
||||
|
||||
The game was never planned to be released in public,
|
||||
so it's designed for the LAMP stack it was originally hosted on.
|
||||
Basically the code assumes some software versions and settings,
|
||||
and will propably break on different configuration.
|
||||
|
||||
REQUIRED SOFTWARE
|
||||
===
|
||||
|
||||
* *Apache 2.x*, with enabled mod_rewrite and .htaccess files.
|
||||
* *PHP 5.2.x* with settings like in attached php.ini file.
|
||||
* *MySQL 5.1*, may also work on other 5.x versions.
|
||||
* *PHPTAL 1.2.1* - newer releases are propably also safe.
|
||||
* The hosting **MUST** also offer crontab or other similar services.
|
||||
|
||||
INSTALLATION
|
||||
===
|
||||
|
||||
1. Prepare database tables using attached SQL file.
|
||||
|
||||
2. Configure PHP using attached INI file.
|
||||
|
||||
3. Upload game code into server.
|
||||
|
||||
4. Download PHPTAL library and upload it into lib subdirectory,
|
||||
you should now have `lib/PHPTAL.php`, `lib/PHPTAL/Context.php` etc.
|
||||
|
||||
5. Enter your hosting's configuration panel and set the `public` subdir
|
||||
as a domain root, so other files won't be accessible from the Net.
|
||||
|
||||
6. Configure crontab: set the `cron.php` file to be executed every day.
|
||||
|
||||
7. And now the tricky part: create a config file (or files) and upload
|
||||
it into `cfg` subdirectory. It's a long and weird topic, details below.
|
||||
|
||||
CONFIGURATION
|
||||
===
|
||||
|
||||
The game configuration is handled by the `Daemon_Config` class
|
||||
(`lib/daemon/config.php` file), which uses it to overwrite its public
|
||||
properties. Consult the class' constructor for details.
|
||||
|
||||
The file's content is simple, it should do nothing more than to return
|
||||
an associative array of settings. Here's an example of minimal config:
|
||||
|
||||
<?php
|
||||
return array(
|
||||
'applicationUrl' => 'http://example.com/foo/bar/baz/',
|
||||
'applicationMail' => 'daemon@example.com',
|
||||
'dbHost' => 'localhost',
|
||||
'dbSchema' => 'daemon_db',
|
||||
'dbUser' => 'username',
|
||||
'dbPassword' => 'some_password',
|
||||
);
|
||||
|
||||
The tricky part is the config's filename. As you can see in the class'
|
||||
constructor, it _must_ be exactly the same as the domain on which
|
||||
the game is hosted, plus the `.php` extension.
|
||||
For example, if the game is hosted on `example.com`, then the filename
|
||||
is `example.com.php`. This is designed to prevent accidental overwrites
|
||||
with config for other machines...
|
||||
|
||||
There is also another tricky part: if you execute a script from the
|
||||
command line instead of URL, then the script uses a special `_cron.php`
|
||||
file instead of normal config. So you should create that file too.
|
||||
Or change the `Daemon_Config`'s constructor ;)
|
182
2013/daemon/cron.php
Normal file
182
2013/daemon/cron.php
Normal file
|
@ -0,0 +1,182 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
chdir(dirname(__FILE__));
|
||||
$cfg = require_once './public/_init.php';
|
||||
ini_set('expose_php', '0');
|
||||
ini_set('default_mimetype', '');
|
||||
ini_set('default_charset', '');
|
||||
$dbClient = Daemon::createDbClient($cfg);
|
||||
$dbCfg = new Daemon_DbConfig($dbClient);
|
||||
$forum = new Daemon_Forum($dbClient);
|
||||
|
||||
//cleanup
|
||||
$queries = array(
|
||||
"CREATE TEMPORARY TABLE junk(id INT NOT NULL PRIMARY KEY)",
|
||||
//delete inactive players
|
||||
"INSERT INTO junk(id) SELECT player_id FROM players WHERE last_login < (NOW() - INTERVAL 1 MONTH)",
|
||||
"DELETE FROM players WHERE player_id IN (SELECT id FROM junk)",
|
||||
"DELETE FROM user_agents WHERE player_id IN (SELECT id FROM junk)",
|
||||
"UPDATE characters SET player_id = NULL WHERE player_id IN (SELECT id FROM junk)",
|
||||
"TRUNCATE TABLE junk",
|
||||
//delete inactive characters
|
||||
"INSERT INTO junk(id) SELECT character_id FROM characters WHERE player_id IS NULL OR last_action < (NOW() - INTERVAL 1 MONTH)",
|
||||
"DELETE FROM characters WHERE character_id IN (SELECT id FROM junk)",
|
||||
"DELETE FROM character_data WHERE character_id IN (SELECT id FROM junk)",
|
||||
"DELETE FROM character_missions WHERE character_id IN (SELECT id FROM junk)",
|
||||
"DELETE FROM character_regions WHERE character_id IN (SELECT id FROM junk)",
|
||||
"DELETE FROM character_statistics WHERE character_id IN (SELECT id FROM junk)",
|
||||
"DELETE FROM character_titles WHERE character_id IN (SELECT id FROM junk)",
|
||||
"DELETE FROM combat_units WHERE combat_unit_id IN (SELECT CONCAT('character-', id) FROM junk)",
|
||||
"DELETE FROM inventory WHERE character_id IN (SELECT id FROM junk)",
|
||||
"UPDATE clans SET leader_id = NULL WHERE leader_id IN (SELECT id FROM junk)",
|
||||
"DELETE FROM clan_invitations WHERE character_id IN (SELECT id FROM junk)",
|
||||
"TRUNCATE TABLE junk",
|
||||
//dump abandoned clans & old invitations
|
||||
"DELETE FROM clans WHERE leader_id IS NULL",
|
||||
"DELETE FROM clan_invitations WHERE date_added < (NOW() - INTERVAL 1 WEEK)",
|
||||
);
|
||||
foreach($queries as $sql)
|
||||
$dbClient->query($sql, array());
|
||||
unset($queries);
|
||||
|
||||
//check for endgame
|
||||
if(!$dbCfg->rolloversEnabled)
|
||||
return;
|
||||
|
||||
//create rollover entry
|
||||
$sql = "INSERT INTO rollovers(date_added) VALUES (now())";
|
||||
$dbClient->query($sql);
|
||||
$rolloverId = $dbClient->lastInsertId();
|
||||
|
||||
//give turns
|
||||
$sql = "UPDATE character_data SET turns = LEAST(:limit, turns + :delta)";
|
||||
$params = array('delta' => (int) $dbCfg->turnDelta, 'limit' => (int) $dbCfg->turnLimit);
|
||||
$dbClient->query($sql, $params);
|
||||
|
||||
//run caern sieges
|
||||
$sql = "SELECT l.location_id FROM locations l JOIN character_data cd USING(location_id)
|
||||
WHERE l.type='caern' AND cd.faction_id IS NOT NULL AND cd.faction_id != l.faction_id
|
||||
GROUP BY l.location_id";
|
||||
$locations = $dbClient->selectColumn($sql);
|
||||
foreach ((array) $locations as $siegeLocationId)
|
||||
{
|
||||
$combat = new Daemon_CaernSiege();
|
||||
$combat->attachDbClient($dbClient);
|
||||
$combat->execute($siegeLocationId);
|
||||
$sql = "INSERT INTO battles(rollover_id, location_id, type, combat_log)
|
||||
VALUES (:rolloverId, :locationId, 'caern', :combatLog)";
|
||||
$params = array('rolloverId' => $rolloverId, 'locationId' => $siegeLocationId,
|
||||
'combatLog' => $combat->getCombatLog());
|
||||
$dbClient->query($sql, $params);
|
||||
$dbCfg->siegeLocationId = null;
|
||||
$siegeLocationId = null;
|
||||
unset($combat);
|
||||
}
|
||||
|
||||
//update faction power
|
||||
$decay = (float) $dbCfg->factionDecay;
|
||||
$sql = "UPDATE factions f SET f.power = FLOOR(:decay * f.power) + COALESCE((
|
||||
SELECT SUM(l.faction_value) FROM locations l WHERE l.type='caern' AND l.faction_id=f.faction_id
|
||||
), 0)";
|
||||
$dbClient->query($sql, array('decay' => $decay));
|
||||
|
||||
//activate bosses
|
||||
$sql = "SELECT MAX(level) As max_level, MAX(rank_id) AS max_rank FROM character_data";
|
||||
$row = $dbClient->selectRow($sql, array());
|
||||
$unlockBosses = ($row['max_level'] >= $dbCfg->bossUnlockLevel) && ($row['max_rank'] >= $dbCfg->bossUnlockRank);
|
||||
if($unlockBosses)
|
||||
{
|
||||
$dbClient->query("UPDATE locations SET boss_status='active' WHERE type='boss' AND boss_status != 'defeated'");
|
||||
if(!$dbCfg->endgame)
|
||||
$dbCfg->endgame = 1;
|
||||
}
|
||||
|
||||
//run boss sieges
|
||||
$sql = "SELECT location_id, name FROM locations WHERE type='boss' AND boss_status = 'active'";
|
||||
$locations = $dbClient->selectAll($sql);
|
||||
if($locations)
|
||||
{
|
||||
$factionPowers = array();
|
||||
$sql = "SELECT faction_id, power FROM factions";
|
||||
foreach($dbClient->selectAll($sql) as $row)
|
||||
$factionPowers[$row['faction_id']] = $row['power'];
|
||||
foreach($locations as $row)
|
||||
{
|
||||
$combat = new Daemon_BossCombat();
|
||||
$combat->attachDbClient($dbClient);
|
||||
$combat->execute($row['location_id'], $factionPowers);
|
||||
$combatLog = $combat->getCombatLog();
|
||||
if($combatLog)
|
||||
{
|
||||
$sql = "INSERT INTO battles(rollover_id, location_id, type, combat_log)
|
||||
VALUES (:rolloverId, :locationId, 'boss', :combatLog)";
|
||||
$params = array('rolloverId' => $rolloverId, 'locationId' => $row['location_id'], 'combatLog' => $combatLog);
|
||||
$dbClient->query($sql, $params);
|
||||
$forum->addChat(null, 'public', "Siedziba bossa \"$row[name]\" zaatakowana!");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//check for ending
|
||||
$factions = array();
|
||||
$sql = "SELECT faction_id, name FROM factions";
|
||||
foreach($dbClient->selectAll($sql) as $row)
|
||||
$factions[$row['faction_id']] = array('name' => $row['name'], 'active' => 0, 'defeated' => 0);
|
||||
$sql = "SELECT faction_id, (boss_status!='defeated') AS active
|
||||
FROM locations WHERE type = 'boss' GROUP BY faction_id, active";
|
||||
foreach($dbClient->selectAll($sql) as $row)
|
||||
{
|
||||
if($row['active'])
|
||||
$factions[$row['faction_id']]['active']++;
|
||||
else
|
||||
$factions[$row['faction_id']]['defeated']++;
|
||||
}
|
||||
$active = array();
|
||||
$defeated = array();
|
||||
foreach($factions as $factionId => $row)
|
||||
{
|
||||
if($row['active'] || !$row['defeated'])
|
||||
$active[$factionId] = $row['name'];
|
||||
else
|
||||
$defeated[$factionId] = $row['name'];
|
||||
}
|
||||
$endgame = (count($active) < 2);
|
||||
if($endgame)
|
||||
{
|
||||
//final messages
|
||||
$active = implode(', ', $active);
|
||||
switch($active)
|
||||
{
|
||||
case 'blue':
|
||||
$msg = "Rewolucja została stłumiona. Niech żyje Porządek!";
|
||||
break;
|
||||
case 'red':
|
||||
$msg = "Cesarz został obalony. Niech żyje Rewolucja!";
|
||||
break;
|
||||
default:
|
||||
$msg = "Wojna dobiegła końca, lecz brak w niej zwycięzców. Czas pokaże, kto zajmie miejsce dawnych potęg...";
|
||||
}
|
||||
$forum->addChat(null, 'public', $msg);
|
||||
//cleanup
|
||||
$dbCfg->globalMessage = $msg;
|
||||
$dbCfg->rolloversEnabled = 0;
|
||||
$dbCfg->turnDelta = 0;
|
||||
$dbCfg->defaultRespawn = '';
|
||||
$sql = "UPDATE character_data SET turns = 0, location_id = NULL";
|
||||
$dbClient->query($sql);
|
||||
$sql = "TRUNCATE TABLE character_regions";
|
||||
$dbClient->query($sql);
|
||||
}
|
||||
|
||||
//update rollover data
|
||||
$sql = "SELECT COUNT(1) FROM players";
|
||||
$nPlayers = $dbClient->selectValue($sql);
|
||||
$sql = "SELECT COUNT(1) FROM characters";
|
||||
$nChars = $dbClient->selectValue($sql);
|
||||
$sql = "SELECT COUNT(1) FROM clans";
|
||||
$nClans = $dbClient->selectValue($sql);
|
||||
$sql = "UPDATE rollovers SET players_total = :players, characters_total = :chars,
|
||||
clans_total = :clans WHERE rollover_id = :id";
|
||||
$params = array('id' => $rolloverId, 'players' => $nPlayers, 'chars' => $nChars, 'clans' => $nClans);
|
||||
$dbClient->query($sql, $params);
|
525
2013/daemon/daemon.sql
Normal file
525
2013/daemon/daemon.sql
Normal file
|
@ -0,0 +1,525 @@
|
|||
CREATE TABLE battles (
|
||||
battle_id int NOT NULL AUTO_INCREMENT,
|
||||
rollover_id smallint NOT NULL,
|
||||
location_id varchar(32) NOT NULL,
|
||||
"type" enum('caern','boss') NOT NULL,
|
||||
combat_log text NOT NULL,
|
||||
PRIMARY KEY (battle_id),
|
||||
KEY rollover_id (rollover_id,battle_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE characters (
|
||||
character_id int NOT NULL AUTO_INCREMENT,
|
||||
player_id int DEFAULT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
gender enum('f','m','n') NOT NULL,
|
||||
date_created timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
last_action datetime NOT NULL DEFAULT '0000-00-00 00:00:00',
|
||||
show_player tinyint(1) NOT NULL DEFAULT 0,
|
||||
last_mail_id int NOT NULL DEFAULT 0,
|
||||
clan_id varchar(8) DEFAULT NULL,
|
||||
avatar_url tinytext,
|
||||
quote text,
|
||||
description text,
|
||||
PRIMARY KEY (character_id),
|
||||
UNIQUE KEY "name" ("name"),
|
||||
KEY clan (clan_id,character_id),
|
||||
KEY date_created (date_created,character_id),
|
||||
KEY player_id (player_id,character_id),
|
||||
KEY last_action (last_action)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE character_data (
|
||||
character_id int NOT NULL,
|
||||
location_id varchar(32) DEFAULT NULL COMMENT 'current location',
|
||||
faction_id varchar(32) DEFAULT NULL,
|
||||
faction_points smallint NOT NULL DEFAULT 0,
|
||||
rank_id tinyint DEFAULT NULL,
|
||||
turns smallint NOT NULL DEFAULT 30,
|
||||
gold_purse int NOT NULL DEFAULT 0,
|
||||
gold_bank int NOT NULL DEFAULT 0,
|
||||
"level" smallint NOT NULL DEFAULT 0,
|
||||
xp_free int NOT NULL DEFAULT 29,
|
||||
xp_used int NOT NULL DEFAULT 0,
|
||||
deaths int NOT NULL DEFAULT 0,
|
||||
health smallint NOT NULL DEFAULT 0,
|
||||
health_max smallint NOT NULL DEFAULT 70,
|
||||
mana smallint NOT NULL DEFAULT 0,
|
||||
mana_max smallint NOT NULL DEFAULT 35,
|
||||
mana_regen smallint NOT NULL DEFAULT 1,
|
||||
a_str smallint NOT NULL DEFAULT 7,
|
||||
a_dex smallint NOT NULL DEFAULT 7,
|
||||
a_vit smallint NOT NULL DEFAULT 7,
|
||||
a_pwr smallint NOT NULL DEFAULT 7,
|
||||
a_wil smallint NOT NULL DEFAULT 7,
|
||||
s_pstr smallint NOT NULL DEFAULT 0,
|
||||
s_patk smallint NOT NULL DEFAULT 0,
|
||||
s_pdef smallint NOT NULL DEFAULT 0,
|
||||
s_pres smallint NOT NULL DEFAULT 0,
|
||||
s_preg smallint NOT NULL DEFAULT 0,
|
||||
s_mstr smallint NOT NULL DEFAULT 0,
|
||||
s_matk smallint NOT NULL DEFAULT 0,
|
||||
s_mdef smallint NOT NULL DEFAULT 0,
|
||||
s_mres smallint NOT NULL DEFAULT 0,
|
||||
s_mreg smallint NOT NULL DEFAULT 0,
|
||||
sp_scout tinyint NOT NULL DEFAULT 0,
|
||||
sp_identify tinyint NOT NULL DEFAULT 0,
|
||||
sp_vchar tinyint NOT NULL DEFAULT 0,
|
||||
sp_vmonster tinyint NOT NULL DEFAULT 0,
|
||||
sp_vitem tinyint NOT NULL DEFAULT 0,
|
||||
combat_unit_id varchar(32) DEFAULT NULL,
|
||||
location_event text COMMENT 'event parameters',
|
||||
PRIMARY KEY (character_id),
|
||||
KEY "level" ("level",character_id),
|
||||
KEY xp_used (xp_used,character_id),
|
||||
KEY faction_id (faction_id,character_id),
|
||||
KEY location_id (location_id,character_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE character_missions (
|
||||
character_id int NOT NULL,
|
||||
rollover_id int NOT NULL,
|
||||
service_id varchar(32) NOT NULL,
|
||||
"type" enum('monster','item') NOT NULL,
|
||||
params varchar(32) NOT NULL,
|
||||
progress enum('active','completed','rewarded') NOT NULL DEFAULT 'active',
|
||||
PRIMARY KEY (character_id,rollover_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE character_regions (
|
||||
character_id int NOT NULL,
|
||||
region_id varchar(32) NOT NULL,
|
||||
PRIMARY KEY (character_id,region_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE character_statistics (
|
||||
character_id int NOT NULL,
|
||||
missions smallint NOT NULL DEFAULT 0,
|
||||
duel_wins smallint NOT NULL DEFAULT 0,
|
||||
duel_losses smallint NOT NULL DEFAULT 0,
|
||||
kills_mob1 smallint NOT NULL DEFAULT 0,
|
||||
kills_mob2 smallint NOT NULL DEFAULT 0,
|
||||
kills_mob3 smallint NOT NULL DEFAULT 0,
|
||||
kills_mob4 smallint NOT NULL DEFAULT 0,
|
||||
PRIMARY KEY (character_id),
|
||||
KEY duel_wins (duel_wins,character_id),
|
||||
KEY duel_losses (duel_losses,character_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE character_titles (
|
||||
character_id int NOT NULL,
|
||||
title_id varchar(32) NOT NULL,
|
||||
PRIMARY KEY (character_id,title_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE chat (
|
||||
message_id int NOT NULL AUTO_INCREMENT,
|
||||
date_added timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
channel_id varchar(255) NOT NULL,
|
||||
sender_id int DEFAULT NULL,
|
||||
content text NOT NULL,
|
||||
PRIMARY KEY (message_id),
|
||||
KEY sort (channel_id,message_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE clans (
|
||||
clan_id varchar(8) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
date_created timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
leader_id int DEFAULT NULL,
|
||||
description text,
|
||||
PRIMARY KEY (clan_id),
|
||||
UNIQUE KEY "name" ("name")
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE clan_invitations (
|
||||
clan_id varchar(32) NOT NULL,
|
||||
character_id int NOT NULL,
|
||||
date_added timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
description text,
|
||||
PRIMARY KEY (clan_id,character_id),
|
||||
KEY search (character_id,clan_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE combat_units (
|
||||
combat_unit_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
faction_id varchar(32) DEFAULT NULL,
|
||||
health int NOT NULL DEFAULT 70,
|
||||
health_max int NOT NULL DEFAULT 70,
|
||||
str1 smallint NOT NULL DEFAULT 7,
|
||||
atk1 smallint NOT NULL DEFAULT 7,
|
||||
type1 enum('p','m') DEFAULT 'p',
|
||||
count1 smallint NOT NULL DEFAULT 1,
|
||||
sp1_type varchar(32) DEFAULT NULL,
|
||||
sp1_param smallint DEFAULT NULL,
|
||||
str2 smallint NOT NULL DEFAULT 7,
|
||||
atk2 smallint NOT NULL DEFAULT 7,
|
||||
type2 enum('p','m') DEFAULT NULL,
|
||||
count2 smallint NOT NULL DEFAULT 0,
|
||||
sp2_type varchar(32) DEFAULT NULL,
|
||||
sp2_param smallint DEFAULT NULL,
|
||||
pdef smallint NOT NULL DEFAULT 7,
|
||||
pres smallint NOT NULL DEFAULT 7,
|
||||
mdef smallint NOT NULL DEFAULT 7,
|
||||
mres smallint NOT NULL DEFAULT 7,
|
||||
speed smallint NOT NULL DEFAULT 7,
|
||||
armor smallint NOT NULL DEFAULT 0,
|
||||
armor_sp_type varchar(32) DEFAULT NULL,
|
||||
armor_sp_param smallint DEFAULT NULL,
|
||||
regen float NOT NULL DEFAULT 0,
|
||||
PRIMARY KEY (combat_unit_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE duels (
|
||||
duel_id int NOT NULL AUTO_INCREMENT,
|
||||
date_added timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
rollover_id smallint DEFAULT NULL,
|
||||
attacker_id int NOT NULL,
|
||||
defender_id int NOT NULL,
|
||||
"type" enum('normal','arena') NOT NULL,
|
||||
winner enum('a','b') DEFAULT NULL,
|
||||
combat_log text,
|
||||
PRIMARY KEY (duel_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE "events" (
|
||||
event_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
handle varchar(255) DEFAULT NULL,
|
||||
description text,
|
||||
PRIMARY KEY (event_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE factions (
|
||||
faction_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
power smallint NOT NULL DEFAULT 0,
|
||||
PRIMARY KEY (faction_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE faction_ranks (
|
||||
faction_id varchar(32) NOT NULL,
|
||||
rank_id tinyint NOT NULL,
|
||||
min_points smallint NOT NULL DEFAULT 1,
|
||||
title_id varchar(32) DEFAULT NULL,
|
||||
PRIMARY KEY (faction_id,rank_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE inventory (
|
||||
inventory_id int NOT NULL AUTO_INCREMENT,
|
||||
character_id int NOT NULL,
|
||||
item_id varchar(32) NOT NULL,
|
||||
"status" enum('inventory','storage') NOT NULL DEFAULT 'inventory',
|
||||
flags set('bound','identified') NOT NULL,
|
||||
equipped enum('hand_a','hand_b','armor','helmet','gloves','boots','pendant','accesory_a','accesory_b') DEFAULT NULL,
|
||||
PRIMARY KEY (inventory_id),
|
||||
KEY sort (character_id,"status")
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE items (
|
||||
item_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
"type" enum('weapon1h','weapon2h','armor','helmet','gloves','boots','pendant','accesory','item') NOT NULL DEFAULT 'item',
|
||||
"value" int NOT NULL DEFAULT 0,
|
||||
suggested_value float NOT NULL DEFAULT 0,
|
||||
damage_type enum('p','m') DEFAULT NULL,
|
||||
special_type varchar(32) DEFAULT NULL,
|
||||
special_param varchar(255) DEFAULT NULL,
|
||||
pstr_p smallint NOT NULL DEFAULT 0,
|
||||
pstr_c smallint NOT NULL DEFAULT 0,
|
||||
patk_p smallint NOT NULL DEFAULT 0,
|
||||
patk_c smallint NOT NULL DEFAULT 0,
|
||||
pdef_p smallint NOT NULL DEFAULT 0,
|
||||
pdef_c smallint NOT NULL DEFAULT 0,
|
||||
pres_p smallint NOT NULL DEFAULT 0,
|
||||
pres_c smallint NOT NULL DEFAULT 0,
|
||||
mstr_p smallint NOT NULL DEFAULT 0,
|
||||
mstr_c smallint NOT NULL DEFAULT 0,
|
||||
matk_p smallint NOT NULL DEFAULT 0,
|
||||
matk_c smallint NOT NULL DEFAULT 0,
|
||||
mdef_p smallint NOT NULL DEFAULT 0,
|
||||
mdef_c smallint NOT NULL DEFAULT 0,
|
||||
mres_p smallint NOT NULL DEFAULT 0,
|
||||
mres_c smallint NOT NULL DEFAULT 0,
|
||||
armor smallint NOT NULL DEFAULT 0,
|
||||
speed smallint NOT NULL DEFAULT 0,
|
||||
regen smallint NOT NULL DEFAULT 0,
|
||||
description text,
|
||||
PRIMARY KEY (item_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE item_specials (
|
||||
special_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
handle varchar(255) DEFAULT NULL,
|
||||
description text,
|
||||
PRIMARY KEY (special_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE item_templates (
|
||||
id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
pstr_p_p smallint NOT NULL DEFAULT 1,
|
||||
pstr_p_m smallint NOT NULL DEFAULT 1,
|
||||
pstr_c_p smallint NOT NULL DEFAULT 1,
|
||||
pstr_c_m smallint NOT NULL DEFAULT 1,
|
||||
patk_p_p smallint NOT NULL DEFAULT 1,
|
||||
patk_p_m smallint NOT NULL DEFAULT 1,
|
||||
patk_c_p smallint NOT NULL DEFAULT 1,
|
||||
patk_c_m smallint NOT NULL DEFAULT 1,
|
||||
pdef_p_p smallint NOT NULL DEFAULT 1,
|
||||
pdef_p_m smallint NOT NULL DEFAULT 1,
|
||||
pdef_c_p smallint NOT NULL DEFAULT 1,
|
||||
pdef_c_m smallint NOT NULL DEFAULT 1,
|
||||
pres_p_p smallint NOT NULL DEFAULT 1,
|
||||
pres_p_m smallint NOT NULL DEFAULT 1,
|
||||
pres_c_p smallint NOT NULL DEFAULT 1,
|
||||
pres_c_m smallint NOT NULL DEFAULT 1,
|
||||
mstr_p_p smallint NOT NULL DEFAULT 1,
|
||||
mstr_p_m smallint NOT NULL DEFAULT 1,
|
||||
mstr_c_p smallint NOT NULL DEFAULT 1,
|
||||
mstr_c_m smallint NOT NULL DEFAULT 1,
|
||||
matk_p_p smallint NOT NULL DEFAULT 1,
|
||||
matk_p_m smallint NOT NULL DEFAULT 1,
|
||||
matk_c_p smallint NOT NULL DEFAULT 1,
|
||||
matk_c_m smallint NOT NULL DEFAULT 1,
|
||||
mdef_p_p smallint NOT NULL DEFAULT 1,
|
||||
mdef_p_m smallint NOT NULL DEFAULT 1,
|
||||
mdef_c_p smallint NOT NULL DEFAULT 1,
|
||||
mdef_c_m smallint NOT NULL DEFAULT 1,
|
||||
mres_p_p smallint NOT NULL DEFAULT 1,
|
||||
mres_p_m smallint NOT NULL DEFAULT 1,
|
||||
mres_c_p smallint NOT NULL DEFAULT 1,
|
||||
mres_c_m smallint NOT NULL DEFAULT 1,
|
||||
armor_p smallint NOT NULL DEFAULT 1,
|
||||
armor_m smallint NOT NULL DEFAULT 1,
|
||||
speed_p smallint NOT NULL DEFAULT 1,
|
||||
speed_m smallint NOT NULL DEFAULT 1,
|
||||
regen_p smallint NOT NULL DEFAULT 1,
|
||||
regen_m smallint NOT NULL DEFAULT 1,
|
||||
PRIMARY KEY (id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE locations (
|
||||
location_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
"type" enum('normal','arena','caern','boss') NOT NULL DEFAULT 'normal',
|
||||
chance1 smallint NOT NULL DEFAULT 1,
|
||||
chance2 smallint NOT NULL DEFAULT 1,
|
||||
region_id varchar(32) DEFAULT NULL,
|
||||
faction_id varchar(32) DEFAULT NULL,
|
||||
faction_value tinyint NOT NULL DEFAULT 1,
|
||||
description text,
|
||||
picture_url tinytext,
|
||||
boss_id varchar(32) DEFAULT NULL,
|
||||
boss_status enum('hidden','active','defeated') DEFAULT NULL,
|
||||
PRIMARY KEY (location_id),
|
||||
KEY region_id (region_id,location_id),
|
||||
KEY faction_id (faction_id,location_id),
|
||||
KEY "type" ("type",location_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE location_events (
|
||||
location_id varchar(32) NOT NULL,
|
||||
event_id varchar(32) NOT NULL,
|
||||
chance smallint NOT NULL DEFAULT 1,
|
||||
params varchar(255) NOT NULL DEFAULT '',
|
||||
PRIMARY KEY (location_id,event_id),
|
||||
KEY event_id (event_id,location_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE location_monsters (
|
||||
location_id varchar(32) NOT NULL,
|
||||
monster_id varchar(32) NOT NULL,
|
||||
chance smallint NOT NULL DEFAULT 1,
|
||||
PRIMARY KEY (location_id,monster_id),
|
||||
KEY monster_id (monster_id,location_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE location_paths (
|
||||
location_id varchar(32) NOT NULL,
|
||||
destination_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) DEFAULT NULL,
|
||||
cost_gold int NOT NULL DEFAULT 0,
|
||||
cost_mana smallint NOT NULL DEFAULT 0,
|
||||
PRIMARY KEY (location_id,destination_id),
|
||||
KEY destination_id (destination_id,location_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE location_services (
|
||||
location_id varchar(32) NOT NULL,
|
||||
service_id varchar(32) NOT NULL,
|
||||
PRIMARY KEY (location_id,service_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE mail (
|
||||
message_id int NOT NULL AUTO_INCREMENT,
|
||||
date_added timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
sender_id int DEFAULT NULL,
|
||||
recipient_id int NOT NULL,
|
||||
content text NOT NULL,
|
||||
PRIMARY KEY (message_id),
|
||||
KEY sort (recipient_id,message_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE maps (
|
||||
map_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
url varchar(255) NOT NULL,
|
||||
sort smallint NOT NULL DEFAULT 0,
|
||||
PRIMARY KEY (map_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE monsters (
|
||||
monster_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
class smallint NOT NULL DEFAULT 1,
|
||||
"level" smallint NOT NULL DEFAULT 1,
|
||||
gold int NOT NULL DEFAULT 0,
|
||||
chance1 smallint NOT NULL DEFAULT 1,
|
||||
chance2 smallint NOT NULL DEFAULT 1,
|
||||
title_id varchar(255) DEFAULT NULL,
|
||||
combat_unit_id varchar(32) DEFAULT NULL,
|
||||
PRIMARY KEY (monster_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE monster_drops (
|
||||
monster_id varchar(32) NOT NULL,
|
||||
item_id varchar(32) NOT NULL,
|
||||
chance smallint NOT NULL DEFAULT 1,
|
||||
PRIMARY KEY (monster_id,item_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE newsfeed (
|
||||
id varchar(255) NOT NULL,
|
||||
updated timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
|
||||
published timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
|
||||
title varchar(255) DEFAULT NULL,
|
||||
author varchar(255) DEFAULT NULL,
|
||||
content text,
|
||||
PRIMARY KEY (id),
|
||||
KEY published (published)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE parameters (
|
||||
"name" varchar(255) NOT NULL,
|
||||
"value" text NOT NULL,
|
||||
PRIMARY KEY ("name")
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE players (
|
||||
player_id int NOT NULL AUTO_INCREMENT,
|
||||
"name" varchar(255) DEFAULT NULL,
|
||||
login varchar(255) NOT NULL,
|
||||
"password" varchar(255) NOT NULL,
|
||||
date_created timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
last_login datetime DEFAULT NULL,
|
||||
roles set('chat','login') NOT NULL DEFAULT 'chat,login',
|
||||
skin varchar(255) DEFAULT NULL,
|
||||
email varchar(255) DEFAULT NULL,
|
||||
reset_key varchar(255) DEFAULT NULL,
|
||||
reset_until date DEFAULT NULL,
|
||||
reset_password varchar(255) DEFAULT NULL,
|
||||
PRIMARY KEY (player_id),
|
||||
UNIQUE KEY login (login),
|
||||
KEY reset_key (reset_key)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE regions (
|
||||
region_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
respawn_id varchar(32) DEFAULT NULL,
|
||||
picture_url tinytext,
|
||||
PRIMARY KEY (region_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE rollovers (
|
||||
rollover_id smallint NOT NULL AUTO_INCREMENT,
|
||||
date_added timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
players_total smallint NOT NULL DEFAULT 0,
|
||||
characters_total smallint NOT NULL DEFAULT 0,
|
||||
clans_total smallint DEFAULT NULL,
|
||||
PRIMARY KEY (rollover_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE services (
|
||||
service_id varchar(32) NOT NULL,
|
||||
"type" enum('bank','healer','npc','shop','temple') NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
faction_id varchar(32) DEFAULT NULL,
|
||||
rank_id tinyint DEFAULT NULL,
|
||||
description text,
|
||||
PRIMARY KEY (service_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE service_items (
|
||||
service_id varchar(32) NOT NULL,
|
||||
item_id varchar(32) NOT NULL,
|
||||
"type" enum('normal','drop') NOT NULL DEFAULT 'normal',
|
||||
quantity smallint DEFAULT NULL,
|
||||
PRIMARY KEY (service_id,item_id),
|
||||
KEY item_id (item_id,service_id)
|
||||
);
|
||||
|
||||
|
||||
CREATE TABLE spells (
|
||||
spell_id varchar(32) NOT NULL,
|
||||
"name" varchar(255) NOT NULL,
|
||||
max_level tinyint NOT NULL DEFAULT 7,
|
||||
max_cost smallint NOT NULL DEFAULT 10,
|
||||
min_cost smallint NOT NULL DEFAULT 1,
|
||||
handle varchar(255) DEFAULT NULL,
|
||||
PRIMARY KEY (spell_id)
|
||||
);
|
||||
|
||||
INSERT INTO spells (spell_id, `name`, max_level, max_cost, min_cost, handle) VALUES
|
||||
('identify', 'Identyfikacja', 6, 45, 25, 'Identify'),
|
||||
('scout', 'Badanie Terenu', 4, 35, 20, 'Scout'),
|
||||
('vchar', 'Poznanie Postaci', 7, 60, 30, 'ScanCharacter'),
|
||||
('vitem', 'Poznanie Przedmiotu', 6, 40, 20, 'ScanItem'),
|
||||
('vmonster', 'Poznanie Potwora', 5, 40, 20, 'ScanMonster');
|
||||
|
||||
CREATE TABLE titles (
|
||||
title_id varchar(32) NOT NULL,
|
||||
name_f varchar(255) NOT NULL DEFAULT '',
|
||||
name_m varchar(255) NOT NULL DEFAULT '',
|
||||
name_n varchar(255) NOT NULL DEFAULT '',
|
||||
"type" enum('normal','special') NOT NULL DEFAULT 'normal',
|
||||
PRIMARY KEY (title_id),
|
||||
KEY "type" ("type",title_id)
|
||||
);
|
102
2013/daemon/lib/daemon.php
Normal file
102
2013/daemon/lib/daemon.php
Normal file
|
@ -0,0 +1,102 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//container for miscelaneous functions
|
||||
class Daemon
|
||||
{
|
||||
|
||||
|
||||
//class autoloader
|
||||
public static function autoload($className)
|
||||
{
|
||||
$className = mb_strtolower(str_replace('_', DIRECTORY_SEPARATOR, $className));
|
||||
spl_autoload($className, '.php');
|
||||
}
|
||||
|
||||
|
||||
//creates Daemon_DbClient object using specified config
|
||||
public static function createDbClient(Daemon_Config $cfg)
|
||||
{
|
||||
$dsn = sprintf('mysql:host=%s;dbname=%s', $cfg->dbHost, $cfg->dbSchema);
|
||||
$params = array(PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES 'utf8', time_zone = '+1:00'");
|
||||
$dbh = new PDO($dsn, $cfg->dbUser, $cfg->dbPassword, $params);
|
||||
$dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
|
||||
return new Daemon_DbClient($dbh);
|
||||
}
|
||||
|
||||
|
||||
//prepares multiline text for displaying, also inserts some basic tags
|
||||
public static function formatMessage($txt, $markup = false)
|
||||
{
|
||||
$txt = nl2br(htmlspecialchars($txt, ENT_QUOTES));
|
||||
if($markup)
|
||||
{
|
||||
$txt = preg_replace('@\[img\](.+)\[/img\]@uU', '<img src="$1" alt="$1" class="bbcode"/>', $txt);
|
||||
$txt = preg_replace('@\[url=(.+)\](.+)\[/url\]@uU', '<a href="$1" rel="nofollow">$2</a>', $txt);
|
||||
$txt = preg_replace('@\[url\]([img]){0}(.+)\[/url\]@uU', '<a href="$1" rel="nofollow">$1</a>', $txt);
|
||||
$txt = preg_replace('@(^|>|\s)(https://\S+)($|<|\s)@muU', '$1<a href="$2" rel="nofollow">$2</a>$3', $txt);
|
||||
$txt = preg_replace('@(^|>|\s)(http://\S+)($|<|\s)@muU', '$1<a href="$2" rel="nofollow">$2</a>$3', $txt);
|
||||
$txt = preg_replace('@\[b\](.+)\[/b\]@uU', '<b>$1</b>', $txt);
|
||||
$txt = preg_replace('@\[i\](.+)\[/i\]@uU', '<i>$1</i>', $txt);
|
||||
$txt = preg_replace('@\[u\](.+)\[/u\]@uU', '<u>$1</u>', $txt);
|
||||
$txt = preg_replace('@\[s\](.+)\[/s\]@uU', '<s>$1</s>', $txt);
|
||||
$txt = preg_replace('@\[sub\](.+)\[/sub\]@uU', '<sub>$1</sub>', $txt);
|
||||
$txt = preg_replace('@\[sup\](.+)\[/sup\]@uU', '<sup>$1</sup>', $txt);
|
||||
}
|
||||
return $txt;
|
||||
}
|
||||
|
||||
|
||||
//returns value from array, or defaults if it doesn't exist
|
||||
public static function getArrayValue(array $a, $name, $default = null)
|
||||
{
|
||||
return isset($a[$name]) ? $a[$name] : $default;
|
||||
}
|
||||
|
||||
|
||||
//implodes whitespace, optionally preserving newlines
|
||||
public static function normalizeString($string, $preserveNewlines = false)
|
||||
{
|
||||
$string = str_replace(array("\r\n","\r"), "\n", $string); //unix newlines
|
||||
if($preserveNewlines)
|
||||
$string = preg_replace('/[^\S\n]+/', ' ', $string);
|
||||
else $string = preg_replace('/\s+/', ' ', $string);
|
||||
$string = trim($string);
|
||||
return $string;
|
||||
}
|
||||
|
||||
|
||||
//generates a password hash
|
||||
public static function passwordHash($salt, $text)
|
||||
{
|
||||
return sha1($salt . $text);
|
||||
}
|
||||
|
||||
|
||||
//returns random salt for password hashing
|
||||
public static function passwordSalt()
|
||||
{
|
||||
$c0 = ord('0');
|
||||
$cA = ord('a');
|
||||
$cZ = ord('z');
|
||||
$max = 10+$cZ-$cA;
|
||||
$salt = '';
|
||||
for($i = 0; $i < 8; ++$i)
|
||||
{
|
||||
$x = mt_rand(0, $max);
|
||||
if($x < 10)
|
||||
$salt .= chr($c0 + $x);
|
||||
else $salt .= chr($cA + $x - 10);
|
||||
}
|
||||
return $salt;
|
||||
}
|
||||
|
||||
|
||||
//redirects to selected url
|
||||
public static function redirect($url)
|
||||
{
|
||||
session_write_close(); //just in case
|
||||
header('Content-Type: text/html; charset=UTF-8');
|
||||
header(sprintf('Location: %s', $url), true, 303); //"See Other" status
|
||||
printf('<!DOCTYPE html><html lang="en"><title>Redirect</title><p><a href="%s">continue</a></p>', $url);
|
||||
}
|
||||
}
|
100
2013/daemon/lib/daemon/bosscombat.php
Normal file
100
2013/daemon/lib/daemon/bosscombat.php
Normal file
|
@ -0,0 +1,100 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_BossCombat extends Daemon_CaernSiege
|
||||
{
|
||||
public function execute($locationId, array $factionPowers = array())
|
||||
{
|
||||
//read location
|
||||
$location = $this->getLocation($locationId);
|
||||
$bossFactionId = $location['faction_id'];
|
||||
$powerMod = Daemon_Math::factionPowerMult($bossFactionId, $factionPowers);
|
||||
//prepare units
|
||||
$this->kickNeutrals($locationId);
|
||||
$units = $this->getCharacterUnits($locationId);
|
||||
//check for empty caern
|
||||
if(empty($units))
|
||||
return null;
|
||||
$attackers = false;
|
||||
foreach($units as $factionId => $faction)
|
||||
{
|
||||
if($factionId != $bossFactionId)
|
||||
$attackers = true;
|
||||
}
|
||||
if(!$attackers)
|
||||
return null;
|
||||
unset($attackers, $factionId, $faction);
|
||||
//prepare boss
|
||||
$boss = $this->getBossUnit($location['boss_id'], $bossFactionId, $powerMod);
|
||||
if(empty($boss))
|
||||
return null;
|
||||
$units[$bossFactionId][$boss->_id] = $boss;
|
||||
//add monster support
|
||||
$supportCount = 0;
|
||||
foreach($units as $factionId => $faction)
|
||||
{
|
||||
if($factionId != $bossFactionId)
|
||||
$supportCount += count($faction);
|
||||
else
|
||||
$supportCount -= count($faction);
|
||||
}
|
||||
if($supportCount > 0)
|
||||
{
|
||||
$support = $this->getLocationMonsters($locationId, $bossFactionId, $supportCount);
|
||||
foreach($support as $unit)
|
||||
$units[$bossFactionId][$unit->_id] = $unit;
|
||||
}
|
||||
unset($support, $supportCount);
|
||||
//execute combat
|
||||
$this->combatLog = $this->runCombat($units, $bossFactionId);
|
||||
//save characters
|
||||
$this->putCharacterUnits($units);
|
||||
//find winner
|
||||
$winnerId = $this->getWinnerFaction($units);
|
||||
//kick losers
|
||||
$this->kickEnemies($locationId, $winnerId);
|
||||
//update location, send message
|
||||
if($winnerId != $bossFactionId)
|
||||
{
|
||||
$sql = "UPDATE locations SET boss_status='defeated' WHERE location_id=:id";
|
||||
$params = array('id' => $locationId);
|
||||
$this->dbClient->query($sql, $params);
|
||||
$msg = "Boss $boss->name z lokacji $location[name] został pokonany!";
|
||||
$forum = new Daemon_Forum($this->dbClient);
|
||||
$forum->addChat(null, 'public', $msg);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private function getBossUnit($monsterId, $factionId, $powerMod)
|
||||
{
|
||||
//read base stats
|
||||
$sql = "SELECT monster_id, name, combat_unit_id
|
||||
FROM monsters WHERE monster_id=:id";
|
||||
$row = $this->dbClient->selectRow($sql, array('id' => $monsterId));
|
||||
$unit = new Daemon_Combat_Unit();
|
||||
$unit->attachDbClient($this->dbClient);
|
||||
$unit->get(array('combat_unit_id' => $row['combat_unit_id']));
|
||||
$unit->name = $row['name'];
|
||||
$unit->faction_id = $factionId;
|
||||
$unit->_id = 'boss';
|
||||
//modify stats
|
||||
$modified = array(
|
||||
'str1', 'atk1', 'str2', 'atk2',
|
||||
'pdef', 'pres', 'mdef', 'mres',
|
||||
'speed', 'armor', 'regen', 'healthMax',
|
||||
);
|
||||
foreach($modified as $name)
|
||||
$unit->$name *= $powerMod;
|
||||
$unit->health = $unit->healthMax;
|
||||
return $unit;
|
||||
}
|
||||
|
||||
|
||||
private function getLocation($locationId)
|
||||
{
|
||||
$sql = "SELECT l.faction_id, l.boss_id, l.name, f.name AS faction_name
|
||||
FROM locations l JOIN factions f USING(faction_id)
|
||||
WHERE location_id = :id";
|
||||
return $this->dbClient->selectRow($sql, array('id' => $locationId));
|
||||
}
|
||||
}
|
270
2013/daemon/lib/daemon/caernsiege.php
Normal file
270
2013/daemon/lib/daemon/caernsiege.php
Normal file
|
@ -0,0 +1,270 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_CaernSiege
|
||||
{
|
||||
protected $dbClient = null;
|
||||
protected $combatLog;
|
||||
|
||||
|
||||
protected function addCharacters(Daemon_Combat $combat, array $units, $locationFactionId)
|
||||
{
|
||||
foreach($units as $factionId => $faction)
|
||||
{
|
||||
foreach($faction as $unit)
|
||||
{
|
||||
$attacker = ($factionId != $locationFactionId);
|
||||
$combat->addUnit($unit->_id, $unit, $attacker);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function attachDbClient(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
//executes the siege, generates the report
|
||||
public function execute($locationId)
|
||||
{
|
||||
//prepare units
|
||||
$this->kickNeutrals($locationId);
|
||||
$faction = $this->getLocationFaction($locationId);
|
||||
$caernFactionId = $faction['id'];
|
||||
$units = $this->getCharacterUnits($locationId);
|
||||
//check for empty caern
|
||||
if(empty($units))
|
||||
{
|
||||
$this->combatLog = '<p>Caern utracony z braku obrońców.</p>';
|
||||
$winnerId = null;
|
||||
}
|
||||
else
|
||||
{
|
||||
//add monster support
|
||||
$supportCount = 0;
|
||||
foreach($units as $factionId => $faction)
|
||||
{
|
||||
if($factionId != $caernFactionId)
|
||||
$supportCount += count($faction);
|
||||
else
|
||||
$supportCount -= count($faction);
|
||||
}
|
||||
if($supportCount > 0)
|
||||
{
|
||||
$support = $this->getLocationMonsters($locationId, $caernFactionId, $supportCount);
|
||||
foreach($support as $unit)
|
||||
$units[$caernFactionId][$unit->_id] = $unit;
|
||||
}
|
||||
unset($support, $supportCount);
|
||||
//execute combat
|
||||
$this->combatLog = $this->runCombat($units, $caernFactionId);
|
||||
//save characters
|
||||
$this->putCharacterUnits($units);
|
||||
//find winner (units modified by combat)
|
||||
$winnerId = $this->getWinnerFaction($units);
|
||||
if(!$winnerId)
|
||||
$msg = 'utracony';
|
||||
elseif($winnerId != $caernFactionId)
|
||||
$msg = 'przejęty';
|
||||
else
|
||||
$msg = 'utrzymany';
|
||||
$this->combatLog .= "<p><b>Caern $msg!</b></p>";
|
||||
}
|
||||
//kick losers
|
||||
$this->kickEnemies($locationId, $winnerId);
|
||||
//update location
|
||||
$sql = "UPDATE locations SET faction_id=:fid WHERE location_id=:id";
|
||||
$params = array('fid' => $winnerId, 'id' => $locationId);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
protected function getCharacterUnits($locationId)
|
||||
{
|
||||
$units = array();
|
||||
$sql = "SELECT cd.character_id, c.name, cd.faction_id, cd.health, cd.health_max, cd.combat_unit_id
|
||||
FROM character_data cd JOIN characters c USING(character_id)
|
||||
WHERE location_id=:id AND cd.faction_id IS NOT NULL ORDER BY xp_used DESC";
|
||||
$data = $this->dbClient->selectAll($sql, array('id' => $locationId));
|
||||
foreach($data as $row)
|
||||
{
|
||||
$unit = new Daemon_Combat_Unit();
|
||||
$unit->attachDbClient($this->dbClient);
|
||||
$unit->get(array('combat_unit_id' => $row['combat_unit_id']));
|
||||
$unit->name = $row['name'];
|
||||
$unit->faction_id = $row['faction_id'];
|
||||
$unit->health = $row['health_max'];
|
||||
$unit->health_max = $row['health_max'];
|
||||
$unit->_id = $row['character_id'];
|
||||
$units[$row['faction_id']][$unit->_id] = $unit;
|
||||
}
|
||||
return $units;
|
||||
}
|
||||
|
||||
|
||||
public function getCombatLog()
|
||||
{
|
||||
return $this->combatLog;
|
||||
}
|
||||
|
||||
|
||||
protected function getLocationFaction($locationId)
|
||||
{
|
||||
$sql = "SELECT faction_id AS id, f.name
|
||||
FROM locations l JOIN factions f USING(faction_id)
|
||||
WHERE location_id=:id";
|
||||
return $this->dbClient->selectRow($sql, array('id' => $locationId));
|
||||
}
|
||||
|
||||
|
||||
protected function getLocationMonsters($locationId, $factionId, $desiredCount)
|
||||
{
|
||||
$result = array();
|
||||
$sql = "SELECT m.monster_id, m.name, m.combat_unit_id
|
||||
FROM location_monsters lm JOIN monsters m USING(monster_id)
|
||||
WHERE location_id=:id";
|
||||
$mobs = $this->dbClient->selectAll($sql, array('id' => $locationId));
|
||||
if(empty($mobs))
|
||||
return array();
|
||||
for($i = 0; $i < $desiredCount; ++$i)
|
||||
{
|
||||
$row = $mobs[array_rand($mobs)];
|
||||
$unit = new Daemon_Combat_Unit();
|
||||
$unit->attachDbClient($this->dbClient);
|
||||
$unit->get(array('combat_unit_id' => $row['combat_unit_id']));
|
||||
$unit->name = $row['name'];
|
||||
$unit->faction_id = $factionId;
|
||||
$unit->_id = "mob_$i";
|
||||
$result[$unit->_id] = $unit;
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
protected function getWinnerFaction(array $units)
|
||||
{
|
||||
$survivors = array();
|
||||
foreach($units as $factionId => $faction)
|
||||
{
|
||||
$survivors[$factionId] = 0;
|
||||
foreach($faction as $unit)
|
||||
{
|
||||
if($unit->health > 0)
|
||||
$survivors[$unit->faction_id] += 1;
|
||||
}
|
||||
}
|
||||
$winnerId = null;
|
||||
$winnerCount = 0;
|
||||
foreach($survivors as $factionId => $count)
|
||||
{
|
||||
if($winnerCount < $count)
|
||||
{
|
||||
$winnerId = $factionId;
|
||||
$winnerCount = $count;
|
||||
}
|
||||
}
|
||||
return $winnerId;
|
||||
}
|
||||
|
||||
|
||||
//kicks enemies out of the caern
|
||||
public function kickEnemies($locationId, $factionId)
|
||||
{
|
||||
$sql = "UPDATE character_data SET location_id=NULL WHERE location_id=:locationId";
|
||||
$params = array('locationId' => $locationId);
|
||||
if($factionId)
|
||||
{
|
||||
$sql .= " AND faction_id!=:factionId";
|
||||
$params['factionId'] = $factionId;
|
||||
}
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//kicks neutral characters out of the caern
|
||||
protected function kickNeutrals($locationId)
|
||||
{
|
||||
$sql = "UPDATE character_data SET location_id=NULL WHERE location_id=:id AND faction_id IS NULL";
|
||||
$this->dbClient->query($sql, array('id' => $locationId));
|
||||
}
|
||||
|
||||
|
||||
protected function putCharacterUnits(array $units)
|
||||
{
|
||||
$sqlLive = "UPDATE character_data SET health=:hp WHERE character_id=:id";
|
||||
$sqlDie = "UPDATE character_data SET health=0, location_id=null WHERE character_id=:id";
|
||||
foreach($units as $faction)
|
||||
{
|
||||
foreach($faction as $unit)
|
||||
{
|
||||
if(!is_numeric($unit->_id))
|
||||
continue;//monsters have string IDs
|
||||
if($unit->health > 0)
|
||||
{
|
||||
$params = array('id' => $unit->_id, 'hp' => $unit->health);
|
||||
$this->dbClient->query($sqlLive, $params);
|
||||
}
|
||||
else
|
||||
{
|
||||
$params = array('id' => $unit->_id);
|
||||
$this->dbClient->query($sqlDie, $params);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function runCombat(array $units, $locationFactionId)
|
||||
{
|
||||
$combat = new Daemon_Combat();
|
||||
$logger = new Daemon_Combat_Log();
|
||||
$combat->attachLogger($logger);
|
||||
foreach($units as $factionId => $faction)
|
||||
{
|
||||
foreach($faction as $unit)
|
||||
{
|
||||
$attacker = ($factionId != $locationFactionId);
|
||||
$combat->addUnit($unit->_id, $unit, $attacker);
|
||||
}
|
||||
}
|
||||
$combat->execute();
|
||||
foreach($combat->units as &$unit)
|
||||
$unit->health = max(0, ceil($unit->health));
|
||||
//prepare summary
|
||||
$summary = array();
|
||||
$summary[] = '<table class="border">';
|
||||
$summary[] = '<caption>Podsumowanie bitwy</caption>';
|
||||
$summary[] = '<tr>';
|
||||
$summary[] = '<th rowspan="2">Strona</th><th colspan="3">Postać</th>';
|
||||
$summary[] = '<th colspan="3">Wykonane ataki</th><th colspan="3">Otrzymane ataki</th>';
|
||||
$summary[] = '</tr>';
|
||||
$summary[] = '<tr>';
|
||||
$summary[] = '<th>Imię</th><th>Frakcja</th><th>Zdrowie</th>';
|
||||
$summary[] = '<th>Ataki</th><th>Obrażenia</th><th>Średnia</th>';
|
||||
$summary[] = '<th>Ataki</th><th>Obrażenia</th><th>Średnia</th>';
|
||||
$summary[] = '</tr>';
|
||||
foreach($units as $factionId => $faction)
|
||||
{
|
||||
foreach($faction as $unit)
|
||||
{
|
||||
$attackerTxt = $unit->_attacker ? 'atak' : 'obrona';
|
||||
$dmgTotal = $unit->_dmgDealt + $unit->_dmgTaken;
|
||||
$health = max(0, ceil($unit->health_max - $unit->_dmgTaken));
|
||||
$healthPercent = $unit->health_max ? round(100 * $health / $unit->health_max, 2) : 0;
|
||||
$avgDealt = $unit->_cntDealt ? $unit->_dmgDealt / $unit->_cntDealt : null;
|
||||
$avgTaken = $unit->_cntTaken ? $unit->_dmgTaken / $unit->_cntTaken : null;
|
||||
$summary[] = '<tr>';
|
||||
$summary[] = sprintf('<td>%s</td><td>%s</td><td>%s</td><td>%.2f%%</td>',
|
||||
$attackerTxt, $unit->name, $unit->faction_id, $healthPercent);
|
||||
$summary[] = sprintf('<td>%d</td><td>%.3f</td><td>%.3f</td>',
|
||||
$unit->_cntDealt, $unit->_dmgDealt, $avgDealt);
|
||||
$summary[] = sprintf('<td>%d</td><td>%.3f</td><td>%.3f</td>',
|
||||
$unit->_cntTaken, $unit->_dmgTaken, $avgTaken);
|
||||
$summary[] = '</tr>';
|
||||
}
|
||||
}
|
||||
$summary[] = '</table>';
|
||||
return implode('', $summary) . (string) $logger;
|
||||
}
|
||||
}
|
164
2013/daemon/lib/daemon/combat.php
Normal file
164
2013/daemon/lib/daemon/combat.php
Normal file
|
@ -0,0 +1,164 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//combat engine
|
||||
//usage:
|
||||
//$combat = new Daemon_Combat();
|
||||
//$logger = new Daemon_Combat_Log();
|
||||
//$combat->attachLogger($logger);
|
||||
//$combat->addUnit('a', $unit1, true);
|
||||
//$combat->addUnit('b', $unit2, false);
|
||||
//$combat->execute();
|
||||
//$combatLog = (string) $logger;
|
||||
class Daemon_Combat
|
||||
{
|
||||
public $units = array();
|
||||
public $sideA = array();
|
||||
public $sideB = array();
|
||||
public $round = 0;
|
||||
public $roundLimit = 120;
|
||||
public $tickLimit = 1;
|
||||
private $_logger = null;
|
||||
|
||||
|
||||
public function addUnit($unitId, Daemon_Combat_Unit $unit, $attacker)
|
||||
{
|
||||
$unit->attachLogger($this->_logger);
|
||||
$unit->_id = $unitId;
|
||||
$unit->_ticks = 0;
|
||||
$unit->_initiative = mt_rand(0, 32 * $unit->speed);
|
||||
$unit->_target = null;
|
||||
$unit->_threat = array();
|
||||
$unit->_dmgDealt = 0;
|
||||
$unit->_dmgTaken = 0;
|
||||
$this->units[$unitId] = $unit;
|
||||
$unit->_attacker = (bool) $attacker;
|
||||
if($unit->_attacker)
|
||||
{
|
||||
$this->sideA[$unitId] = $unit;
|
||||
$unit->_allies = &$this->sideA;
|
||||
$unit->_enemies = &$this->sideB;
|
||||
}
|
||||
else
|
||||
{
|
||||
$this->sideB[$unitId] = $unit;
|
||||
$unit->_allies = &$this->sideB;
|
||||
$unit->_enemies = &$this->sideA;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function attachLogger(Daemon_Combat_Log $logger)
|
||||
{
|
||||
$this->_logger = $logger;
|
||||
foreach($this->units as $unit)
|
||||
$unit->attachLogger($logger);
|
||||
}
|
||||
|
||||
|
||||
protected function callbackActive($unit)
|
||||
{
|
||||
return $unit->_ticks > $this->tickLimit;
|
||||
}
|
||||
|
||||
|
||||
protected function callbackSpeedSum($prev, $unit)
|
||||
{
|
||||
return $prev + $unit->speed;
|
||||
}
|
||||
|
||||
|
||||
protected function callbackTickCompare($unit1, $unit2)
|
||||
{
|
||||
if($unit1->_ticks == $unit2->_ticks)
|
||||
return $unit1->_initiative - $unit2->_initiative;
|
||||
else return ($unit1->_ticks < $unit2->_ticks) ? -1 : +1;
|
||||
}
|
||||
|
||||
|
||||
protected function callbackTickInc($unit, $key)
|
||||
{
|
||||
if($unit->health > 0)
|
||||
$unit->_ticks += $unit->speed;
|
||||
else $unit->_ticks = null;
|
||||
}
|
||||
|
||||
|
||||
protected function debug($round, array $units)
|
||||
{
|
||||
if($this->_logger)
|
||||
{
|
||||
$result = array("Segment $round");
|
||||
foreach($units as $unit)
|
||||
$result[] = (string) $unit;
|
||||
$this->_logger->add($result);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function execute($noCleanup = false)
|
||||
{
|
||||
if(!$this->units)
|
||||
return;
|
||||
$unitCount = count($this->units);
|
||||
if ($this->_logger)
|
||||
$this->_logger->groupCombat = ($unitCount > 2);
|
||||
$round = 0;
|
||||
$roundLimit = 100 + 10 * $unitCount;
|
||||
$speedSum = array_reduce($this->units, array($this, 'callbackSpeedSum'), 0);
|
||||
$this->tickLimit = 1 + ceil(2 * $speedSum / count($this->units));
|
||||
while($round < $roundLimit)
|
||||
{
|
||||
$victory = false;
|
||||
array_walk($this->units, array($this, 'callbackTickInc'));
|
||||
while($actor = $this->getActiveUnit())
|
||||
{
|
||||
++$round;
|
||||
$actor->_ticks -= $this->tickLimit;
|
||||
$actor->executeRound($round);
|
||||
//victory check, sides should be updated by units
|
||||
$victory = (!count($this->sideA) || !count($this->sideB));
|
||||
if($victory)
|
||||
break;
|
||||
}
|
||||
if($victory)
|
||||
break;
|
||||
}
|
||||
//after-combat regen & fixes
|
||||
if (!$noCleanup)
|
||||
{
|
||||
foreach($this->units as $unit)
|
||||
{
|
||||
if ($unit->health < 1)
|
||||
{
|
||||
$unit->health = 0;
|
||||
}
|
||||
elseif (($unit->regen > 0) && ($unit->health < $unit->health_max))
|
||||
{
|
||||
$unit->health = $unit->health_max;
|
||||
if($this->_logger)
|
||||
$this->_logger->add("<i>$unit->name</i> regeneruje pełnię zdrowia.<br>");
|
||||
}
|
||||
else
|
||||
{
|
||||
$unit->health = Daemon_Math::round($unit->health);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
protected function getActiveUnit()
|
||||
{
|
||||
$active = array_filter($this->units, array($this, 'callbackActive'));
|
||||
uasort($active, array($this, 'callbackTickCompare'));
|
||||
return array_pop($active);
|
||||
}
|
||||
|
||||
|
||||
public function reset()
|
||||
{
|
||||
$this->units = array();
|
||||
$this->sideA = array();
|
||||
$this->sideB = array();
|
||||
}
|
||||
}
|
117
2013/daemon/lib/daemon/combat/log.php
Normal file
117
2013/daemon/lib/daemon/combat/log.php
Normal file
|
@ -0,0 +1,117 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Combat_Log
|
||||
{
|
||||
private $buffer;
|
||||
public $groupCombat;
|
||||
|
||||
|
||||
public function __construct()
|
||||
{
|
||||
$this->clear();
|
||||
}
|
||||
|
||||
|
||||
public function __toString()
|
||||
{
|
||||
return $this->buffer;
|
||||
}
|
||||
|
||||
|
||||
public function add($text)
|
||||
{
|
||||
$this->buffer .= "$text\n";
|
||||
}
|
||||
|
||||
|
||||
public function clear()
|
||||
{
|
||||
$this->buffer = '';
|
||||
}
|
||||
|
||||
|
||||
public static function escape($str)
|
||||
{
|
||||
return htmlspecialchars($str, ENT_QUOTES, 'UTF-8');
|
||||
}
|
||||
|
||||
|
||||
public function txtAttackHit($name, $dmg, $magical, $critical, $poison, $shockDmg, $stun, $vampRegen)
|
||||
{
|
||||
$txt = $critical ? 'Trafienie krytyczne! ' : '';
|
||||
$txt .= sprintf('<i>%s</i> zadaje <b>%.2f</b> obrażeń %s', self::escape($name),
|
||||
$dmg, $magical ? 'magicznych' : 'fizycznych');
|
||||
if($poison)
|
||||
$txt .= ', zatruwając cel';
|
||||
if($stun)
|
||||
$txt .= ', ogłuszając cel';
|
||||
if($vampRegen)
|
||||
$txt .= sprintf(', regenerując <b>%.2f</b> HP', $vampRegen);
|
||||
if($shockDmg)
|
||||
$txt .= sprintf('. Otrzymuje <b>%.2f</b> obrażeń od porażenia', $shockDmg);
|
||||
$txt .= '.<br>';
|
||||
$this->add($txt);
|
||||
}
|
||||
|
||||
|
||||
public function txtAttackMiss($name, $magical)
|
||||
{
|
||||
if($magical)
|
||||
$this->add('Cel odbił zaklęcie.<br>');
|
||||
else $this->add(sprintf('<i>%s</i> chybił.<br>', self::escape($name)));
|
||||
}
|
||||
|
||||
|
||||
public function txtDeath($name, $flawlessName = null)
|
||||
{
|
||||
$txt = sprintf('<i>%s</i> umiera.<br>', $name);
|
||||
if($flawlessName)
|
||||
{
|
||||
$atxt = array('<i>%s</i> ziewa.', '<i>%s</i> śmieje się szyderczo.');
|
||||
$txt .= sprintf($atxt[array_rand($atxt)], self::escape($flawlessName)).'<br>';
|
||||
}
|
||||
$this->add($txt);
|
||||
}
|
||||
|
||||
|
||||
public function txtDemon($regen)
|
||||
{
|
||||
$this->add(sprintf('Demon w zbroi wchłonął zaklęcie. Cel regeneruje %.2f obrażeń.<br>', $regen));
|
||||
}
|
||||
|
||||
|
||||
public function txtPoison($name, $dmg)
|
||||
{
|
||||
$this->add(sprintf('<i>%s</i> otrzymuje %.2f obrażeń od trucizny.<br>', self::escape($name), $dmg));
|
||||
}
|
||||
|
||||
|
||||
public function txtRegen($name, $regen)
|
||||
{
|
||||
$this->add(sprintf('<i>%s</i> regeneruje %.2f obrażeń.<br>', self::escape($name), $regen));
|
||||
}
|
||||
|
||||
|
||||
public function txtRoundFooter()
|
||||
{
|
||||
$this->add('</p>');
|
||||
}
|
||||
|
||||
|
||||
public function txtRoundHeader($round)
|
||||
{
|
||||
$this->add(sprintf('<h3>Akcja %d</h3><p>', $round));
|
||||
}
|
||||
|
||||
|
||||
public function txtTargetHeader($actorName, $targetName)
|
||||
{
|
||||
if($targetName)
|
||||
{
|
||||
if ($this->groupCombat)
|
||||
$this->add(sprintf('<i>%s</i> wybiera cel: <i>%s</i>.<br>',
|
||||
self::escape($actorName), self::escape($targetName)));
|
||||
}
|
||||
else $this->add(sprintf('<i>%s</i> nie ma już przeciwników.<br>', self::escape($actorName)));
|
||||
}
|
||||
}
|
261
2013/daemon/lib/daemon/combat/unit.php
Normal file
261
2013/daemon/lib/daemon/combat/unit.php
Normal file
|
@ -0,0 +1,261 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//combat stats (daemon or monster)
|
||||
class Daemon_Combat_Unit extends Daemon_DbObject_CombatUnit
|
||||
{
|
||||
private $_logger = null;
|
||||
//combat variables
|
||||
public $_id = null;
|
||||
public $_flawless = true;
|
||||
public $_ticks = 0;
|
||||
public $_initiative = 0;
|
||||
public $_poison = 0;
|
||||
public $_attacker = null; //attacker or defender
|
||||
public $_target = null; //current target
|
||||
public $_threat = array(); //current threat
|
||||
public $_allies = array(); //global sideA/sideB list
|
||||
public $_enemies = array(); //global sideB/sideA list
|
||||
public $_cntDealt = 0;
|
||||
public $_dmgDealt = 0;
|
||||
public $_cntTaken = 0;
|
||||
public $_dmgTaken = 0;
|
||||
|
||||
|
||||
public function __toString()
|
||||
{
|
||||
return "[id: $this->_id, name: $this->name, ticks: $this->_ticks, health: $this->health/$this->health_max]";
|
||||
}
|
||||
|
||||
|
||||
public function attachLogger(Daemon_Combat_Log $logger = null)
|
||||
{
|
||||
$this->_logger = $logger;
|
||||
}
|
||||
|
||||
|
||||
protected function calculateAttack(array $params)
|
||||
{
|
||||
//attack count - check for swarm
|
||||
if(self::SP_SWARM == $params['sp_type'])
|
||||
$attackCount = ceil($params['count'] * $this->health / $this->health_max);
|
||||
else $attackCount = $params['count'];
|
||||
//prepare variables
|
||||
$magical = ('m' == $params['type']);
|
||||
if($magical)
|
||||
{
|
||||
$targetDef = $this->_target->mdef;
|
||||
$targetRes = $this->_target->mres;
|
||||
$armor = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
$targetDef = $this->_target->pdef;
|
||||
$targetRes = $this->_target->pres;
|
||||
$armor = $this->_target->armor;
|
||||
if(self::SP_ETHER == $params['sp_type'])
|
||||
$armor *= 1 - $params['sp_param']/100;
|
||||
}
|
||||
//calculate basic data
|
||||
$toHit = 100 * $params['atk'] / ($params['atk'] + $targetDef);
|
||||
$baseDmg = $params['str'] * $params['str'] / ($params['str'] + $targetRes);
|
||||
//faction effects
|
||||
if($this->faction_id && $this->_target->faction_id && ($this->faction_id != $this->_target->faction_id))
|
||||
{
|
||||
if(self::SP_FACTION == $params['sp_type'])
|
||||
$baseDmg *= 1 + $params['sp_param']/100;
|
||||
if(self::SP_FACTION == $this->_target->armor_sp_type)
|
||||
$baseDmg /= 1 + $this->_target->armor_sp_param/100;
|
||||
}
|
||||
//execute attacks
|
||||
for($i=0; $i < $attackCount; $i++)
|
||||
{
|
||||
$d100 = mt_rand(0,99);
|
||||
//check for demon
|
||||
$demon = $magical && (self::SP_DEMON == $this->_target->armor_sp_type);
|
||||
if($demon && mt_rand(0,99) < $this->_target->armor_sp_param)
|
||||
{
|
||||
$regen = min($this->_target->health_max - $this->_target->health, $baseDmg * $this->_target->armor_sp_param / 100);
|
||||
$this->_target->health += $regen;
|
||||
if($this->_logger)
|
||||
$this->_logger->txtDemon($regen);
|
||||
}
|
||||
//check for hit
|
||||
elseif($d100 < $toHit)
|
||||
{
|
||||
//calculate damage
|
||||
$critical = $d100>45;
|
||||
if($critical)
|
||||
{
|
||||
$dmgMult = 2;
|
||||
if(self::SP_BLOODY == $params['sp_type'])
|
||||
$dmgMult += $params['sp_param']/100;
|
||||
}
|
||||
else $dmgMult = 1 + mt_rand(0,127)/256;
|
||||
$dmg = max(0, $baseDmg * $dmgMult - $armor);
|
||||
$this->_target->health -= $dmg;
|
||||
//update statistics
|
||||
$this->_target->_flawless = false;
|
||||
$this->_target->_cntTaken += 1;
|
||||
$this->_target->_dmgTaken += $dmg;
|
||||
$this->_cntDealt += 1;
|
||||
$this->_dmgDealt += $dmg;
|
||||
//check for poison
|
||||
if(self::SP_POISON == $params['sp_type'])
|
||||
{
|
||||
$poison = $dmg>0 ? $params['sp_param'] : 0;
|
||||
if(self::SP_ANTIPOISON == $this->_target->armor_sp_type)
|
||||
$poison *= 1 - $this->_target->armor_sp_param / 100;
|
||||
$this->_target->_poison += $poison;
|
||||
}
|
||||
else $poison = 0;
|
||||
//check for shock
|
||||
if(self::SP_SHOCK == $this->_target->armor_sp_type)
|
||||
{
|
||||
$shockDmg = $dmg * $this->_target->armor_sp_param / 100;
|
||||
$this->health -= $shockDmg;
|
||||
}
|
||||
else $shockDmg = 0;
|
||||
//check for stun
|
||||
$stun = $critical && (self::SP_STUN == $params['sp_type']);
|
||||
if($stun)
|
||||
$this->_target->_ticks = 0;
|
||||
//check for vampirism
|
||||
if(self::SP_VAMPIRE == $params['sp_type'])
|
||||
{
|
||||
$vampRegen = min($this->health_max - $this->health, $dmg * $params['sp_param']/100);
|
||||
if(self::SP_ANTIVAMP == $this->_target->armor_sp_type)
|
||||
$vampRegen *= 1 - $this->_target->armor_sp_param / 100;
|
||||
$this->health += $vampRegen;
|
||||
}
|
||||
else $vampRegen = 0;
|
||||
//print info
|
||||
if($this->_logger)
|
||||
{
|
||||
$this->_logger->txtAttackHit($this->name, $dmg, $magical, $critical,
|
||||
$poison, $shockDmg, $stun, $vampRegen);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if($this->_logger)
|
||||
$this->_logger->txtAttackMiss($this->name, $magical);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
protected function executeAttacks()
|
||||
{
|
||||
if(!$this->_target)
|
||||
return;
|
||||
$this->_target->_threat[$this->_id] = $this;
|
||||
if($this->count1 && $this->type1)
|
||||
{
|
||||
$attackParams = array(
|
||||
'str' => $this->str1,
|
||||
'atk' => $this->atk1,
|
||||
'type' => $this->type1,
|
||||
'count' => $this->count1,
|
||||
'sp_type' => $this->sp1_type,
|
||||
'sp_param' => $this->sp1_param,
|
||||
);
|
||||
$this->calculateAttack($attackParams);
|
||||
}
|
||||
if($this->count2 && $this->type2)
|
||||
{
|
||||
$attackParams = array(
|
||||
'str' => $this->str2,
|
||||
'atk' => $this->atk2,
|
||||
'type' => $this->type2,
|
||||
'count' => $this->count2,
|
||||
'sp_type' => $this->sp2_type,
|
||||
'sp_param' => $this->sp2_param,
|
||||
);
|
||||
$this->calculateAttack($attackParams);
|
||||
}
|
||||
//check for target death
|
||||
if($this->_target->health <= 0)
|
||||
{
|
||||
$this->_target->_ticks = null;
|
||||
unset($this->_threat[$this->_target->_id]);
|
||||
unset($this->_enemies[$this->_target->_id]);
|
||||
if($this->_logger)
|
||||
$this->_logger->txtDeath($this->_target->name, $this->_flawless ? $this->name : null);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function executeRound($round)
|
||||
{
|
||||
if($this->_logger)
|
||||
$this->_logger->txtRoundHeader($round);
|
||||
$this->regen();
|
||||
$this->pickTarget();
|
||||
if($this->_target)
|
||||
$this->executeAttacks();
|
||||
$this->poison();
|
||||
if($this->_logger)
|
||||
$this->_logger->txtRoundFooter();
|
||||
}
|
||||
|
||||
|
||||
protected function pickTarget()
|
||||
{
|
||||
//clear old target
|
||||
$this->_target = null;
|
||||
//try current threat
|
||||
while($this->_threat && !$this->_target)
|
||||
{
|
||||
$targetId = array_rand($this->_threat);
|
||||
$this->_target = $this->_threat[$targetId];
|
||||
if($this->_target->health <= 0) //killed by someone else
|
||||
{
|
||||
$this->_target = null;
|
||||
unset($this->_threat[$targetId]);
|
||||
}
|
||||
}
|
||||
//no threat, try other enemies
|
||||
if($this->_enemies && !$this->_target)
|
||||
{
|
||||
$targetId = array_rand($this->_enemies);
|
||||
$this->_target = $this->_enemies[$targetId];
|
||||
}
|
||||
//print message
|
||||
if($this->_logger)
|
||||
{
|
||||
if($this->_target)
|
||||
$this->_logger->txtTargetHeader($this->name, $this->_target->name);
|
||||
else $this->_logger->txtTargetHeader($this->name, null);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
protected function poison()
|
||||
{
|
||||
if($this->_poison)
|
||||
{
|
||||
$dmg = $this->_poison * $this->_poison / ($this->_poison + $this->pres);
|
||||
$this->health -= $dmg;
|
||||
if($this->_logger)
|
||||
$this->_logger->txtPoison($this->name, $dmg);
|
||||
if($this->health <= 0)
|
||||
{
|
||||
unset($this->_allies[$this->_id]);
|
||||
if($this->_logger)
|
||||
$this->_logger->txtDeath($this->name, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
protected function regen()
|
||||
{
|
||||
if($this->regen && $this->health < $this->health_max)
|
||||
{
|
||||
$delta = min($this->health_max - $this->health, $this->regen);
|
||||
$this->health += $delta;
|
||||
if($this->_logger)
|
||||
$this->_logger->txtRegen($this->name, $delta);
|
||||
}
|
||||
}
|
||||
}
|
56
2013/daemon/lib/daemon/config.php
Normal file
56
2013/daemon/lib/daemon/config.php
Normal file
|
@ -0,0 +1,56 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Config
|
||||
{
|
||||
public $applicationRoot;
|
||||
public $applicationTitle = 'Daemon 2';
|
||||
public $applicationUrl;
|
||||
public $applicationMail;
|
||||
public $dbHost;
|
||||
public $dbSchema;
|
||||
public $dbUser;
|
||||
public $dbPassword;
|
||||
public $dbPrefix;
|
||||
public $minifyHtml = false;
|
||||
public $sessionName = 'sessid';
|
||||
public $tsDelta = 0.5;
|
||||
|
||||
|
||||
public function __construct($applicationRoot = null)
|
||||
{
|
||||
$this->applicationRoot = (string) $applicationRoot;
|
||||
$hostname = mb_strtolower(getenv('SERVER_NAME'));
|
||||
if(!$hostname)
|
||||
$hostname = '_cron';
|
||||
$fileName = $hostname . '.php';
|
||||
$this->loadFile($this->getFilePath('cfg', $fileName));
|
||||
}
|
||||
|
||||
|
||||
//loads config from file
|
||||
public function loadFile($path)
|
||||
{
|
||||
if(is_readable($path))
|
||||
{
|
||||
$data = (array) include $path;
|
||||
foreach($data as $key=>$value)
|
||||
$this->$key = $value;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//implodes parameters into relative path and prepends it with root
|
||||
public function getFilePath(/*...*/)
|
||||
{
|
||||
$aPath = array_filter(func_get_args());
|
||||
array_unshift($aPath, $this->applicationRoot);
|
||||
return implode(DIRECTORY_SEPARATOR, $aPath);
|
||||
}
|
||||
|
||||
|
||||
//generates URL from relative path
|
||||
public function getUrl($path)
|
||||
{
|
||||
return $path ? "$this->applicationUrl$path" : $this->applicationUrl;
|
||||
}
|
||||
}
|
158
2013/daemon/lib/daemon/controller.php
Normal file
158
2013/daemon/lib/daemon/controller.php
Normal file
|
@ -0,0 +1,158 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//prototype for page controller
|
||||
class Daemon_Controller
|
||||
{
|
||||
//global objects
|
||||
protected $cfg = null;
|
||||
protected $dbClient = null;
|
||||
protected $dbCfg = null;
|
||||
protected $activeCharacter = null;
|
||||
protected $characterData = null;
|
||||
protected $location = null;
|
||||
protected $player = null;
|
||||
protected $view = null;
|
||||
//execution parameters
|
||||
protected $disableMessages = false;
|
||||
protected $disablePlayer = false;
|
||||
protected $requireActiveChar = false;
|
||||
protected $requireAuthentication = false;
|
||||
protected $requireFactionMatch = false;
|
||||
protected $requireLocation = false;
|
||||
protected $requireNoEvents = false;
|
||||
protected $requiredRole = null;
|
||||
//output parameters
|
||||
protected $pageOutputMode = Daemon_View::MODE_HTML;
|
||||
protected $pageSubtitle = null;
|
||||
protected $pageSubtitleDetails = null;
|
||||
protected $pageSubtitleUseQuery = false;
|
||||
protected $pageTemplatePath;
|
||||
|
||||
|
||||
final public function __construct(Daemon_Config $cfg)
|
||||
{
|
||||
$this->cfg = $cfg;
|
||||
session_name($this->cfg->sessionName);
|
||||
session_cache_limiter(null);
|
||||
session_start();
|
||||
$this->dbClient = Daemon::createDbClient($this->cfg);
|
||||
$this->dbCfg = new Daemon_DbConfig($this->dbClient);
|
||||
if(!$this->disablePlayer)
|
||||
{
|
||||
$this->player = new Daemon_DbObject_Player($this->dbClient);
|
||||
$this->activeCharacter = $this->player->getActiveCharacter();
|
||||
$this->activeCharacter->updateLastAction();
|
||||
$this->characterData = $this->activeCharacter->getCharacterData();
|
||||
$this->location = $this->characterData->getLocation();
|
||||
}
|
||||
$this->view = new Daemon_View($this->cfg);
|
||||
}
|
||||
|
||||
|
||||
//checks last action's timestamp
|
||||
final private function checkActionTimestamp()
|
||||
{
|
||||
$lastAction = isset($_SESSION['ts']) ? $_SESSION['ts'] : 0.0;
|
||||
$_SESSION['ts'] = microtime(true);
|
||||
return (bool) ($_SESSION['ts'] >= $lastAction + $this->cfg->tsDelta);
|
||||
}
|
||||
|
||||
|
||||
final public function execute()
|
||||
{
|
||||
//prepare controller
|
||||
$this->prepareModel();
|
||||
$this->validatePlayer();
|
||||
//check last action's timestamp
|
||||
if($_POST && !$this->checkActionTimestamp())
|
||||
{
|
||||
Daemon_MsgQueue::add('Operacja anulowana: za duża częstość.');
|
||||
$_POST = array();
|
||||
}
|
||||
//execute commands
|
||||
$cmdExecuted = (bool) $this->runCommands();
|
||||
//display page
|
||||
$this->prepareView();
|
||||
if($this->pageSubtitleUseQuery)
|
||||
{
|
||||
if($qs = getenv('QUERY_STRING'))
|
||||
$this->pageSubtitleDetails = urldecode($qs);
|
||||
}
|
||||
$this->view->setPageTitle($this->pageSubtitle, $this->pageSubtitleDetails, $cmdExecuted);
|
||||
if(!$this->disablePlayer)
|
||||
{
|
||||
$this->view->setGameHeader($this->player->getPlayerId(),
|
||||
$this->activeCharacter, $this->characterData, $this->location);
|
||||
$this->view->setPageSkin($this->player->skin);
|
||||
}
|
||||
else $this->view->setPageSkin(null);
|
||||
if(!$this->disableMessages)
|
||||
$messages = Daemon_MsgQueue::getAll();
|
||||
else $messages = array();
|
||||
if($this->dbCfg->globalMessage)
|
||||
$messages[] = $this->dbCfg->globalMessage;
|
||||
$this->view->setMessages($messages);
|
||||
$this->view->display($this->pageTemplatePath, $this->pageOutputMode);
|
||||
}
|
||||
|
||||
|
||||
//page-specific
|
||||
protected function prepareModel()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
//page-specific
|
||||
protected function prepareView()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
//page-specific
|
||||
protected function runCommands()
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
final private function validatePlayer()
|
||||
{
|
||||
if($this->disablePlayer)
|
||||
return;
|
||||
if($this->requireAuthentication && !$this->player->getPlayerId())
|
||||
{
|
||||
Daemon_MsgQueue::add('Strona dostępna tylko dla zalogowanych użytkowników.');
|
||||
Daemon::redirect($this->cfg->getUrl(null));
|
||||
exit;
|
||||
}
|
||||
if($this->requireActiveChar && !$this->player->getCharacterId())
|
||||
{
|
||||
Daemon_MsgQueue::add('Musisz najpierw wybrać aktywną postać.');
|
||||
Daemon::redirect($this->cfg->getUrl('account'));
|
||||
exit;
|
||||
}
|
||||
if($this->requiredRole && !$this->player->hasRole($this->requiredRole))
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie masz uprawnień do korzystania z tej funkcji.');
|
||||
Daemon::redirect($this->cfg->getUrl('account'));
|
||||
exit;
|
||||
}
|
||||
if($this->requireLocation && !$this->location->location_id)
|
||||
{
|
||||
Daemon::redirect($this->cfg->getUrl('respawn'));
|
||||
exit;
|
||||
}
|
||||
if($this->requireNoEvents && $this->characterData->getLocationEvent())
|
||||
{
|
||||
Daemon::redirect($this->cfg->getUrl('map'));
|
||||
exit;
|
||||
}
|
||||
if($this->requireFactionMatch && $this->location->faction_id && $this->characterData->faction_id
|
||||
&& ($this->location->faction_id != $this->characterData->faction_id))
|
||||
{
|
||||
Daemon_MsgQueue::add('Odejdź! Nie przyjmujemy takich jak ty!');
|
||||
Daemon::redirect($this->cfg->getUrl('map'));
|
||||
exit;
|
||||
}
|
||||
}
|
||||
}
|
148
2013/daemon/lib/daemon/dbclient.php
Normal file
148
2013/daemon/lib/daemon/dbclient.php
Normal file
|
@ -0,0 +1,148 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//abstraction for standard db queries
|
||||
class Daemon_DbClient
|
||||
{
|
||||
protected $dbh;
|
||||
|
||||
|
||||
public function __construct(PDO $dbHandle)
|
||||
{
|
||||
$this->dbh = $dbHandle;
|
||||
}
|
||||
|
||||
|
||||
//reads maximum length of columns of selected table
|
||||
public function getColumnMaxLength($table, $column)
|
||||
{
|
||||
$sql = 'SELECT CHARACTER_MAXIMUM_LENGTH FROM information_schema.COLUMNS
|
||||
WHERE TABLE_SCHEMA = SCHEMA() AND TABLE_NAME = :table AND COLUMN_NAME = :column';
|
||||
$params = array('table' => $table, 'column' => $column);
|
||||
return $this->selectColumn($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//returns internal PDO handle
|
||||
public function getDbHandle()
|
||||
{
|
||||
return $this->dbh;
|
||||
}
|
||||
|
||||
|
||||
//internal exception handler
|
||||
private function exceptionHandler(PDOException $e, $duplicateMsg = null)
|
||||
{
|
||||
//prepare params
|
||||
$sqlstate = $e->getCode();
|
||||
$dbMessage = $e->getMessage();
|
||||
//check error type
|
||||
if('23000' == $sqlstate && false !== stripos($dbMessage, 'duplicate'))
|
||||
{
|
||||
$message = $duplicateMsg ? $duplicateMsg : 'Wybrany obiekt już istnieje.';
|
||||
Daemon_MsgQueue::add($message);
|
||||
}
|
||||
else throw $e;
|
||||
}
|
||||
|
||||
|
||||
//executes a query, returns the statement resource
|
||||
public function execute($sql, array $params = array(), $duplicateMsg = null)
|
||||
{
|
||||
try
|
||||
{
|
||||
$sth = $this->dbh->prepare($sql);
|
||||
foreach((array)$params as $name => $value)
|
||||
$sth->bindValue(':'.$name, $value, self::paramType($value));
|
||||
$sth->execute();
|
||||
return $sth;
|
||||
}
|
||||
catch(PDOException $e)
|
||||
{
|
||||
$this->exceptionHandler($e, $duplicateMsg);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//returns ID of last inserted row
|
||||
public function lastInsertId()
|
||||
{
|
||||
return $this->dbh->lastInsertId();
|
||||
}
|
||||
|
||||
|
||||
//returns appriopriate PDO::PARAM_X constant
|
||||
public static function paramType($value)
|
||||
{
|
||||
if(is_null($value))
|
||||
return PDO::PARAM_NULL;
|
||||
elseif(is_int($value))
|
||||
return PDO::PARAM_INT;
|
||||
else return PDO::PARAM_STR;
|
||||
}
|
||||
|
||||
|
||||
//executes a generic non-select query
|
||||
public function query($sql, array $params = array(), $duplicateMsg = null)
|
||||
{
|
||||
$sth = $this->execute($sql, $params, $duplicateMsg);
|
||||
return !is_null($sth);
|
||||
}
|
||||
|
||||
|
||||
//quotes value for safe use in query
|
||||
public function quote($value)
|
||||
{
|
||||
return $this->dbh->quote($value, self::paramType($value));
|
||||
}
|
||||
|
||||
|
||||
//select multiple rows from table
|
||||
public function selectAll($sql, array $params = array())
|
||||
{
|
||||
$sth = $this->execute($sql, $params);
|
||||
if(is_null($sth))
|
||||
return null;
|
||||
return $sth->fetchAll(PDO::FETCH_ASSOC);
|
||||
}
|
||||
|
||||
|
||||
//select single column from table
|
||||
public function selectColumn($sql, array $params = array())
|
||||
{
|
||||
$sth = $this->execute($sql, $params);
|
||||
if(is_null($sth))
|
||||
return null;
|
||||
return $sth->fetchAll(PDO::FETCH_COLUMN, 0);
|
||||
}
|
||||
|
||||
|
||||
//select single row from table (as array)
|
||||
public function selectRow($sql, array $params = array())
|
||||
{
|
||||
$sth = $this->execute($sql, $params);
|
||||
if(is_null($sth))
|
||||
return null;
|
||||
return $sth->fetch(PDO::FETCH_ASSOC);
|
||||
}
|
||||
|
||||
|
||||
//select single row from table (as object)
|
||||
public function selectObject($sql, array $params = array(), $className = 'stdClass')
|
||||
{
|
||||
$sth = $this->execute($sql, $params);
|
||||
if(is_null($sth))
|
||||
return null;
|
||||
return $sth->fetchObject($className);
|
||||
}
|
||||
|
||||
|
||||
//select single value from table
|
||||
public function selectValue($sql, array $params = array())
|
||||
{
|
||||
$sth = $this->execute($sql, $params);
|
||||
if(is_null($sth))
|
||||
return null;
|
||||
return $sth->fetchColumn(0);
|
||||
}
|
||||
}
|
87
2013/daemon/lib/daemon/dbconfig.php
Normal file
87
2013/daemon/lib/daemon/dbconfig.php
Normal file
|
@ -0,0 +1,87 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//manager for game world variables
|
||||
class Daemon_DbConfig
|
||||
{
|
||||
private $dbClient;
|
||||
private $data;
|
||||
|
||||
|
||||
public function __construct(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
public function __get($name)
|
||||
{
|
||||
return $this->get($name);
|
||||
}
|
||||
|
||||
|
||||
public function __set($name, $value)
|
||||
{
|
||||
return $this->set($name, $value);
|
||||
}
|
||||
|
||||
|
||||
public function get($name)
|
||||
{
|
||||
if(!isset($this->data[$name]))
|
||||
{
|
||||
$sql = "SELECT value FROM parameters WHERE name=:name";
|
||||
$params = array('name' => $name);
|
||||
$this->data[$name] = $this->dbClient->selectValue($sql, $params);
|
||||
}
|
||||
return $this->data[$name];
|
||||
}
|
||||
|
||||
|
||||
public function set($name, $value)
|
||||
{
|
||||
if (empty($value))
|
||||
$value = '';
|
||||
$sql = "INSERT INTO parameters(name, value) VALUES (:name, :value) ON DUPLICATE KEY UPDATE value=:value";
|
||||
$params = array('name' => $name, 'value' => $value);
|
||||
$this->dbClient->query($sql, $params);
|
||||
$this->data[$name] = $value;
|
||||
}
|
||||
|
||||
|
||||
public function getGeneratorWeights($type)
|
||||
{
|
||||
$keys = array(
|
||||
'pstr_p', 'pstr_c', 'patk_p', 'patk_c', 'pdef_p', 'pdef_c', 'pres_p', 'pres_c',
|
||||
'mstr_p', 'mstr_c', 'matk_p', 'matk_c', 'mdef_p', 'mdef_c', 'mres_p', 'mres_c',
|
||||
'armor', 'speed', 'regen', 'special_param');
|
||||
return $this->getGeneratorOptions("w_$type", $keys);
|
||||
}
|
||||
|
||||
|
||||
private function getGeneratorOptions($key, array $keys)
|
||||
{
|
||||
$result = json_decode($this->get("generator_$key"), true);
|
||||
if (!is_array($result))
|
||||
$result = array();
|
||||
foreach ($keys as $key)
|
||||
{
|
||||
if (empty($result[$key]))
|
||||
$result[$key] = 0;
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
public function setGeneratorWeights($type, array $options)
|
||||
{
|
||||
$this->setGeneratorOptions("w_$type", $options);
|
||||
}
|
||||
|
||||
|
||||
private function setGeneratorOptions($key, array $options)
|
||||
{
|
||||
foreach ($options as &$val)
|
||||
$val = floatval(str_replace(',', '.', $val));
|
||||
$this->set("generator_$key", json_encode($options));
|
||||
}
|
||||
}
|
108
2013/daemon/lib/daemon/dbobject.php
Normal file
108
2013/daemon/lib/daemon/dbobject.php
Normal file
|
@ -0,0 +1,108 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//active record pattern
|
||||
class Daemon_DbObject
|
||||
{
|
||||
protected $_dbClient;
|
||||
protected $_tableName;
|
||||
protected $_index = array();//names of index columns
|
||||
|
||||
|
||||
public function __construct()
|
||||
{
|
||||
if($params = func_get_args())
|
||||
$this->import($params);
|
||||
}
|
||||
|
||||
|
||||
public function attachDbClient(Daemon_DbClient $dbClient = null)
|
||||
{
|
||||
$this->_dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
//deletes object data from database
|
||||
public function delete()
|
||||
{
|
||||
$cond = array();
|
||||
$params = array();
|
||||
foreach($this->_index as $col)
|
||||
{
|
||||
$cond[] = "$col=:$col";
|
||||
$params[$col] = $this->$col;
|
||||
}
|
||||
$cond = implode(' AND ', $cond);
|
||||
if(!$cond)
|
||||
throw new RuntimeException('Index not specified.');
|
||||
$sql = "DELETE FROM $this->_tableName WHERE $cond";
|
||||
$this->_dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//retrieves object data from database
|
||||
public function get(array $params, $ignoreDuplicates = false)
|
||||
{
|
||||
if(!$params)
|
||||
throw new RuntimeException('Params not specified.');
|
||||
$cond = array();
|
||||
foreach(array_keys($params) as $key)
|
||||
$cond[] = "$key=:$key";
|
||||
$cond = implode(' AND ', $cond);
|
||||
$sql = "SELECT * FROM $this->_tableName WHERE $cond ORDER BY RAND() LIMIT 2";
|
||||
$data = $this->_dbClient->selectAll($sql, $params);
|
||||
if(is_array($data) && isset($data[0]))
|
||||
{
|
||||
if(!$ignoreDuplicates && (count($data) > 1))
|
||||
throw new RuntimeException('Multiple rows found.');
|
||||
foreach($data[0] as $key => $val)
|
||||
$this->$key = $val;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//copies params into object data
|
||||
public function import($params)
|
||||
{
|
||||
$keys = array_keys(get_object_vars($this));
|
||||
foreach($keys as $key)
|
||||
{
|
||||
if(isset($params[$key]) && ($key[0] != '_'))
|
||||
$this->$key = $params[$key];
|
||||
}
|
||||
$this->validate();
|
||||
}
|
||||
|
||||
|
||||
//stores object data in the database
|
||||
public function put()
|
||||
{
|
||||
$this->validate();
|
||||
$cols = array();
|
||||
$vals = array();
|
||||
$mods = array();
|
||||
$params = array();
|
||||
foreach($this as $col => $val)
|
||||
{
|
||||
if($col[0] != '_')
|
||||
{
|
||||
$cols[] = $col;
|
||||
$vals[] = ":$col";
|
||||
if(!in_array($col, $this->_index))
|
||||
$mods[] = "$col=:$col";
|
||||
$params[$col] = $val;
|
||||
}
|
||||
}
|
||||
$cols = implode(', ', $cols);
|
||||
$vals = implode(', ', $vals);
|
||||
$mods = implode(', ', $mods);
|
||||
if($mods)
|
||||
$sql = "INSERT INTO $this->_tableName ($cols) VALUES ($vals) ON DUPLICATE KEY UPDATE $mods";
|
||||
else $sql = "REPLACE INTO $this->_tableName ($cols) VALUES ($vals)";
|
||||
$this->_dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//checks object data
|
||||
public function validate() {}
|
||||
}
|
165
2013/daemon/lib/daemon/dbobject/character.php
Normal file
165
2013/daemon/lib/daemon/dbobject/character.php
Normal file
|
@ -0,0 +1,165 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_Character extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'characters';
|
||||
protected $_index = array('character_id');
|
||||
public $character_id;
|
||||
public $player_id;
|
||||
public $name;
|
||||
public $gender;
|
||||
public $date_created;
|
||||
public $last_action;
|
||||
public $show_player;
|
||||
public $last_mail_id;
|
||||
public $clan_id;
|
||||
public $avatar_url;
|
||||
public $quote;
|
||||
public $description;
|
||||
private $_player;
|
||||
private $_characterData;
|
||||
|
||||
|
||||
public function attachPlayer(Daemon_DbObject_Player $player)
|
||||
{
|
||||
$this->_player = $player;
|
||||
}
|
||||
|
||||
|
||||
//checks character's inbox for new messages
|
||||
public function checkMail()
|
||||
{
|
||||
if(!$this->character_id)
|
||||
return false;
|
||||
$sql = "SELECT COUNT(1) FROM mail WHERE message_id > COALESCE(:lastMailId, 0) AND recipient_id = :charId";
|
||||
$params = array('lastMailId' => $this->last_mail_id, 'charId' => $this->character_id);
|
||||
return $this->_dbClient->selectValue($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//try to create a new clan (id or name may be already taken)
|
||||
public function createClan($clanId, $name)
|
||||
{
|
||||
$clanId = Daemon::normalizeString($clanId, false);
|
||||
$name = Daemon::normalizeString($name, false);
|
||||
$validId = $this->validateClanId($clanId);
|
||||
$validName = $this->validateClanId($name);
|
||||
if($validId && $validName)
|
||||
{
|
||||
$sql = "INSERT INTO clans(clan_id, name, leader_id) VALUES (:id, :name, :leaderId)";
|
||||
$params = array('id' => $clanId, 'name' => $name, 'leaderId' => $this->character_id);
|
||||
if($this->_dbClient->query($sql, $params, 'Wybrany ID lub nazwa klanu są już zajęte.'))
|
||||
{
|
||||
$this->clan_id = $clanId;
|
||||
$this->put();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//returns DbObject_CharacterData instance
|
||||
public function getCharacterData()
|
||||
{
|
||||
if(!$this->_characterData)
|
||||
{
|
||||
$this->_characterData = new Daemon_DbObject_CharacterData();
|
||||
$this->_characterData->attachDbClient($this->_dbClient);
|
||||
if($this->character_id)
|
||||
$this->_characterData->get(array('character_id' => $this->character_id));
|
||||
$this->_characterData->_characterName = $this->name;
|
||||
$this->_characterData->_gender = $this->gender;
|
||||
}
|
||||
return $this->_characterData;
|
||||
}
|
||||
|
||||
|
||||
//returns a channel=>writeAccess array of channels allowed for character
|
||||
public function getForumChannels()
|
||||
{
|
||||
$cdata = $this->getCharacterData();
|
||||
$channels = array('public' => array('name' => 'publiczne', 'writable' => false));
|
||||
if($this->character_id)
|
||||
{
|
||||
$channels['public']['writable'] = $this->_player->hasRole('chat');
|
||||
}
|
||||
if($cdata->faction_id)
|
||||
{
|
||||
$channelId = 'f/'.$cdata->faction_id;
|
||||
$channels[$channelId] = array('name' => 'frakcyjne', 'writable' => $this->_player->hasRole('chat'));
|
||||
}
|
||||
if($this->clan_id)
|
||||
{
|
||||
$channelId = 'c/'.$this->clan_id;
|
||||
$channels[$channelId] = array('name' => 'klanowe', 'writable' => $this->_player->hasRole('chat'));
|
||||
}
|
||||
return $channels;
|
||||
}
|
||||
|
||||
|
||||
//reads a list of invitations
|
||||
public function getInvitations()
|
||||
{
|
||||
$sql = "SELECT i.clan_id, c.name AS clan_name, i.description
|
||||
FROM clan_invitations i JOIN clans c USING(clan_id)
|
||||
WHERE i.character_id=:id";
|
||||
$params = array('id' => $this->character_id);
|
||||
return $this->_dbClient->selectAll($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//sends invitation to specified clan
|
||||
public function inviteClan($clanId, $description, Daemon_Forum $forum)
|
||||
{
|
||||
if(!$description)
|
||||
$description = null;
|
||||
$sql = "SELECT leader_id FROM clans WHERE clan_id=:id";
|
||||
$leaderId = $this->_dbClient->selectValue($sql, array('id' => $clanId));
|
||||
if($leaderId)
|
||||
{
|
||||
$sql = "INSERT IGNORE INTO clan_invitations(clan_id, character_id, description)
|
||||
VALUES (:clanId, :charId, :description) ON DUPLICATE KEY UPDATE description=:description";
|
||||
$params = array('clanId' => $clanId, 'charId' => $this->character_id,
|
||||
'description' => $description);
|
||||
$this->_dbClient->query($sql, $params);
|
||||
$msg = "Postać $this->name pragnie dołączyć do klanu.";
|
||||
$forum->addMailById(null, $leaderId, $msg);
|
||||
}
|
||||
else Daemon_MsgQueue::add('Wybrany klan nie istnieje lub nie ma przywódcy.');
|
||||
}
|
||||
|
||||
|
||||
public function updateLastAction()
|
||||
{
|
||||
if($this->character_id)
|
||||
{
|
||||
$sql = "UPDATE characters SET last_action = NOW() WHERE character_id=:id";
|
||||
$this->_dbClient->query($sql, array('id' => $this->character_id));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//checks clan id validity
|
||||
private function validateClanId($input)
|
||||
{
|
||||
$maxLength = $this->_dbClient->getColumnMaxLength('clans', 'clan_id');
|
||||
if(!$input)
|
||||
Daemon_MsgQueue::add('Musisz podać ID klanu.');
|
||||
elseif(iconv_strlen($input) > $maxLength)
|
||||
Daemon_MsgQueue::add('Wybrany ID jest za długi.');
|
||||
else return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//checks clan name validity
|
||||
private function validateClanName($input)
|
||||
{
|
||||
$maxLength = $this->_dbClient->getColumnMaxLength('clans', 'name');
|
||||
if(!$input)
|
||||
Daemon_MsgQueue::add('Musisz podać nazwę klanu.');
|
||||
elseif(iconv_strlen($input) > $maxLength)
|
||||
Daemon_MsgQueue::add('Wybrana nazwa jest za długa.');
|
||||
else return true;
|
||||
return false;
|
||||
}
|
||||
}
|
609
2013/daemon/lib/daemon/dbobject/characterdata.php
Normal file
609
2013/daemon/lib/daemon/dbobject/characterdata.php
Normal file
|
@ -0,0 +1,609 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_CharacterData extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'character_data';
|
||||
protected $_index = array('character_id');
|
||||
public $_characterName = null;
|
||||
public $_gender = null;
|
||||
public $character_id;
|
||||
public $location_id;
|
||||
public $faction_id, $faction_points, $rank_id;
|
||||
public $turns;
|
||||
public $gold_purse, $gold_bank;
|
||||
public $level, $xp_free, $xp_used;
|
||||
public $deaths, $health, $health_max;
|
||||
public $mana, $mana_max, $mana_regen;
|
||||
public $a_str, $a_dex, $a_vit, $a_pwr, $a_wil;
|
||||
public $s_pstr, $s_patk, $s_pdef, $s_pres, $s_preg;
|
||||
public $s_mstr, $s_matk, $s_mdef, $s_mres, $s_mreg;
|
||||
public $sp_scout, $sp_identify, $sp_vchar, $sp_vmonster, $sp_vitem;
|
||||
protected $location_event; //json packed
|
||||
public $combat_unit_id;
|
||||
private $_combatUnit;
|
||||
|
||||
|
||||
//executes selected event, returns event log
|
||||
public function attack(Daemon_View $view, $targetId, $locationType)
|
||||
{
|
||||
if(!$this->checkTurnCosts())
|
||||
return null;
|
||||
$combat = new Daemon_Duel();
|
||||
$combat->attachCharacterData($this);
|
||||
$combat->attachDbClient($this->_dbClient);
|
||||
$combat->execute($view, $locationType, $targetId);
|
||||
return $combat->getCombatLog();
|
||||
}
|
||||
|
||||
|
||||
//checks of character can attack selected target
|
||||
public function canAttack(array $target, $rolloverId, $withMessages)
|
||||
{
|
||||
//check Id
|
||||
if($this->character_id == $target['character_id'])
|
||||
{
|
||||
if($withMessages)
|
||||
Daemon_MsgQueue::add('Samobójstwo?');
|
||||
return false;
|
||||
}
|
||||
//check location
|
||||
if($this->location_id != $target['location_id'])
|
||||
{
|
||||
if($withMessages)
|
||||
Daemon_MsgQueue::add('Cel opuścił już tą lokację.');
|
||||
return false;
|
||||
}
|
||||
//check levels
|
||||
if(4 * $this->xp_used > 5 * $target['xp_used'])
|
||||
{
|
||||
if($withMessages)
|
||||
Daemon_MsgQueue::add('Cel jest za słaby.');
|
||||
return false;
|
||||
}
|
||||
if(5 * $this->xp_used < 4 * $target['xp_used'])
|
||||
{
|
||||
if($withMessages)
|
||||
Daemon_MsgQueue::add('Cel jest za silny.');
|
||||
return false;
|
||||
}
|
||||
//check previous attacks
|
||||
$cond = "attacker_id=:attackerId AND defender_id=:defenderId";
|
||||
$params = array('attackerId' => $this->character_id, 'defenderId' => $target['character_id']);
|
||||
if($rolloverId)
|
||||
{
|
||||
$cond .= " AND rollover_id=:rolloverId";
|
||||
$params['rolloverId'] = $rolloverId;
|
||||
}
|
||||
$sql = "SELECT COUNT(duel_id) FROM duels WHERE $cond";
|
||||
if($this->_dbClient->selectValue($sql, $params))
|
||||
{
|
||||
if($withMessages)
|
||||
Daemon_MsgQueue::add('Cel już był atakowany przez ciebie w tym przeliczeniu.');
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//updates turns, gold & mana; returns check result
|
||||
public function checkTurnCosts($costGold = 0, $costMana = 0)
|
||||
{
|
||||
if($this->turns < 1)
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie masz dostępnych tur.');
|
||||
return false;
|
||||
}
|
||||
if($this->gold_purse < $costGold)
|
||||
{
|
||||
Daemon_MsgQueue::add('Masz za mało zlota.');
|
||||
return false;
|
||||
}
|
||||
if($this->mana < $costMana)
|
||||
{
|
||||
Daemon_MsgQueue::add('Masz za mało zlota.');
|
||||
return false;
|
||||
}
|
||||
$this->turns -= 1;
|
||||
$this->gold_purse -= $costGold;
|
||||
$this->mana -= $costMana;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//checks of target can be attacked, returns combat type (null for error)
|
||||
public function getCombatType(array $target, $locationType)
|
||||
{
|
||||
//check location type
|
||||
if('normal' != $locationType)
|
||||
return 'arena';
|
||||
//check factions
|
||||
if($this->faction_id && ($this->faction_id == $target['faction_id']))
|
||||
return 'arena';
|
||||
//no restrictions, normal fight
|
||||
return 'normal';
|
||||
}
|
||||
|
||||
|
||||
//returns Daemon_DbObject_CombatUnit instance
|
||||
public function getCombatUnit($full = false)
|
||||
{
|
||||
if(!$this->_combatUnit)
|
||||
{
|
||||
$this->_combatUnit = $full ? new Daemon_Combat_Unit() : new Daemon_DbObject_CombatUnit();
|
||||
$this->_combatUnit->attachDbClient($this->_dbClient);
|
||||
if($this->character_id)
|
||||
{
|
||||
if(!$this->combat_unit_id)
|
||||
$this->combat_unit_id = "character-$this->character_id";
|
||||
$this->_combatUnit->get(array('combat_unit_id' => $this->combat_unit_id));
|
||||
}
|
||||
$this->_combatUnit->combat_unit_id = $this->combat_unit_id;
|
||||
$this->_combatUnit->name = $this->_characterName;
|
||||
$this->_combatUnit->faction_id = $this->faction_id;
|
||||
$this->_combatUnit->health = $this->health;
|
||||
$this->_combatUnit->health_max = $this->health_max;
|
||||
}
|
||||
return $this->_combatUnit;
|
||||
}
|
||||
|
||||
|
||||
//calculates "real" level from level & health
|
||||
public function getEffectiveLevel($addFaction)
|
||||
{
|
||||
$factionMult = 0.1; //magic number!
|
||||
$level = $this->level;
|
||||
if($addFaction)
|
||||
$level *= 1 + $factionMult * $this->rank_id;
|
||||
if($this->health_max)
|
||||
$level = round($level * $this->health / $this->health_max);
|
||||
return $level;
|
||||
}
|
||||
|
||||
|
||||
//checks mission history for last mission's data
|
||||
public function getLastMission($maxProgress)
|
||||
{
|
||||
$sql = "SELECT m.*, s.name AS service_name
|
||||
FROM character_missions m LEFT JOIN services s USING(service_id)
|
||||
WHERE character_id=:id AND progress<=:maxProgress
|
||||
ORDER BY rollover_id DESC LIMIT 1";
|
||||
$params = array('id' => $this->character_id, 'maxProgress' => $maxProgress);
|
||||
if($row = $this->_dbClient->selectRow($sql, $params))
|
||||
{
|
||||
$row['_target'] = $this->getMissionTarget($row['type'], $row['params']);
|
||||
$row['_name'] = $this->getMissionName($row['type'], $row['_target']);
|
||||
$row['_statusName'] = Daemon_Dictionary::$missionProgress[$row['progress']];
|
||||
return $row;
|
||||
}
|
||||
else return null;
|
||||
}
|
||||
|
||||
|
||||
private function getMissionName($type, $name)
|
||||
{
|
||||
switch($type)
|
||||
{
|
||||
case'monster':
|
||||
return "pokonaj potwora: $name";
|
||||
case'item':
|
||||
return "przynieś przedmiot: $name";
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private function getMissionTarget($type, $params)
|
||||
{
|
||||
switch($type)
|
||||
{
|
||||
case'monster':
|
||||
$sql = "SELECT name FROM monsters WHERE monster_id=:id";
|
||||
return $this->_dbClient->selectValue($sql, array('id' => $params));
|
||||
case'item':
|
||||
$sql = "SELECT name FROM items WHERE item_id=:id";
|
||||
return $this->_dbClient->selectValue($sql, array('id' => $params));
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//returns a DbObject_Location instance representing current location
|
||||
public function getLocation()
|
||||
{
|
||||
$object = new Daemon_DbObject_Location();
|
||||
$object->attachDbClient($this->_dbClient);
|
||||
$object->attachCharacterData($this);
|
||||
if($this->character_id)
|
||||
$object->get(array('location_id' => $this->location_id));
|
||||
return $object;
|
||||
}
|
||||
|
||||
|
||||
public function getLocationEvent()
|
||||
{
|
||||
return json_decode($this->location_event, true);
|
||||
}
|
||||
|
||||
|
||||
//fetches a list of possible respawn locations
|
||||
public function getRespawns($defaultRespawn)
|
||||
{
|
||||
$sql = "SELECT location_id, name FROM locations WHERE location_id = :defaultRespawn
|
||||
OR location_id IN (
|
||||
SELECT r.respawn_id FROM regions r
|
||||
JOIN character_regions cr ON cr.region_id=r.region_id AND cr.character_id=:characterId
|
||||
)
|
||||
OR location_id IN (
|
||||
SELECT l.location_id FROM character_regions cr
|
||||
JOIN locations l ON cr.region_id=l.region_id AND cr.character_id=:characterId
|
||||
WHERE l.type='caern' AND l.faction_id=:factionId
|
||||
)";
|
||||
$params = array('characterId' => $this->character_id, 'defaultRespawn' => $defaultRespawn,
|
||||
'factionId' => $this->faction_id);
|
||||
if($data = $this->_dbClient->selectAll($sql, $params))
|
||||
{
|
||||
$result = array();
|
||||
foreach($data as $row)
|
||||
$result[$row['location_id']] = $row['name'];
|
||||
return $result;
|
||||
}
|
||||
else return array();
|
||||
}
|
||||
|
||||
|
||||
public function getSpells()
|
||||
{
|
||||
$sql = "SELECT spell_id, name FROM spells ORDER BY name";
|
||||
$data = $this->_dbClient->selectAll($sql);
|
||||
foreach($data as &$row)
|
||||
{
|
||||
$col = "sp_$row[spell_id]";
|
||||
$row['_cost'] = isset($this->$col) ? $this->$col : null;
|
||||
$row['_cast'] = ($row['_cost'] <= $this->mana);
|
||||
}
|
||||
return $data;
|
||||
}
|
||||
|
||||
|
||||
//increases selected attribute if there is enough xp
|
||||
public function improveAttribute($key)
|
||||
{
|
||||
$col = "a_$key";
|
||||
if(isset($this->$col))
|
||||
{
|
||||
$cost = $this->$col;
|
||||
if($cost <= $this->xp_free)
|
||||
{
|
||||
$this->$col += 1;
|
||||
$this->xp_used += $cost;
|
||||
$this->xp_free -= $cost;
|
||||
$this->resetCombatStats();
|
||||
$this->put();
|
||||
}
|
||||
else Daemon_MsgQueue::add('Nie masz dość doświadczenia.');
|
||||
}
|
||||
else Daemon_MsgQueue::add('Wybrana cecha nie istnieje.');
|
||||
}
|
||||
|
||||
|
||||
//increases faction reputation & rank
|
||||
public function improveReputation($factionId, $delta)
|
||||
{
|
||||
//join faction if needed
|
||||
if(!$this->faction_id)
|
||||
{
|
||||
$sql = "SELECT name FROM factions WHERE faction_id=:id";
|
||||
$factionName = $this->_dbClient->selectValue($sql, array('id' => $factionId));
|
||||
$this->faction_id = $factionId;
|
||||
Daemon_MsgQueue::add("Dołączasz do frakcji: $factionName.");
|
||||
}
|
||||
//raise reputation
|
||||
$this->faction_points += $delta;
|
||||
//check for new rank
|
||||
$sql = "SELECT r.rank_id, r.title_id, t.name_$this->_gender AS title_name
|
||||
FROM faction_ranks r LEFT JOIN titles t USING(title_id)
|
||||
WHERE faction_id=:id
|
||||
AND rank_id = (SELECT MAX(rank_id) FROM faction_ranks WHERE faction_id=:id AND min_points <= :points)";
|
||||
$params = array('id' => $factionId, 'points' => $this->faction_points);
|
||||
$newRank = $this->_dbClient->selectRow($sql, $params);
|
||||
if($newRank && ($newRank['rank_id'] > (int) $this->rank_id))
|
||||
{
|
||||
$this->rank_id = $newRank['rank_id'];
|
||||
if($newRank['title_id'])
|
||||
Daemon_MsgQueue::add("Zdobywasz nową rangę: $newRank[title_name] (poziom $newRank[rank_id]).");
|
||||
else Daemon_MsgQueue::add("Zdobywasz nową rangę (poziom $newRank[rank_id]).");
|
||||
}
|
||||
else Daemon_MsgQueue::add("Rośnie twoja reputacja we frakcji.");
|
||||
}
|
||||
|
||||
|
||||
//increases selected skill if there is enough xp
|
||||
public function improveSkill($key)
|
||||
{
|
||||
$col = "s_$key";
|
||||
if(isset($this->$col))
|
||||
{
|
||||
$cost = $this->$col;
|
||||
if($cost > 0)
|
||||
{
|
||||
if($cost <= $this->xp_free)
|
||||
{
|
||||
$this->$col += 1;
|
||||
$this->xp_used += $cost;
|
||||
$this->xp_free -= $cost;
|
||||
$this->resetCombatStats();
|
||||
$this->put();
|
||||
}
|
||||
else Daemon_MsgQueue::add('Nie masz dość doświadczenia.');
|
||||
}
|
||||
else Daemon_MsgQueue::add('Nie znasz jeszcze tej umiejętności.');
|
||||
}
|
||||
else Daemon_MsgQueue::add('Wybrana umiejętność nie istnieje.');
|
||||
}
|
||||
|
||||
|
||||
//updates combat stats with equipment bonuses
|
||||
private function loadEquipmentBonuses()
|
||||
{
|
||||
//prepare variables
|
||||
$unit = $this->getCombatUnit();
|
||||
$inventory = new Daemon_Inventory($this->_dbClient, $this);
|
||||
$zweihander = false;
|
||||
$attackBonusKeys = array(
|
||||
'pstr_p', 'pstr_c', 'patk_p', 'patk_c',
|
||||
'mstr_p', 'mstr_c', 'matk_p', 'matk_c',
|
||||
);
|
||||
$modWpn1 = array_fill_keys($attackBonusKeys, 0);
|
||||
$modWpn2 = array_fill_keys($attackBonusKeys, 0);
|
||||
$armorBonusKeys = array(
|
||||
'pdef_p', 'pdef_c', 'pres_p', 'pres_c',
|
||||
'mdef_p', 'mdef_c', 'mres_p', 'mres_c',
|
||||
'armor', 'speed', 'regen',
|
||||
);
|
||||
$modArmor = array_fill_keys($armorBonusKeys, 0);
|
||||
//reset hands & armor
|
||||
$unit->type1 = 'p';
|
||||
$unit->count1 = 1;
|
||||
$unit->sp1_type = null;
|
||||
$unit->sp1_param = null;
|
||||
$unit->type2 = 'p';
|
||||
$unit->count2 = 1;
|
||||
$unit->sp2_type = null;
|
||||
$unit->sp2_param = null;
|
||||
$unit->armor_sp_type = null;
|
||||
$unit->armor_sp_param = null;
|
||||
//find equipped items, calculate equipment bonuses
|
||||
$sql = "SELECT item_id, equipped FROM inventory WHERE character_id=:id AND equipped IS NOT NULL";
|
||||
$params = array('id' => $this->character_id);
|
||||
foreach($this->_dbClient->selectAll($sql, $params) AS $row)
|
||||
{
|
||||
$item = new Daemon_DbObject_Item();
|
||||
$item->attachDbClient($this->_dbClient);
|
||||
$item->get(array('item_id' => $row['item_id']));
|
||||
switch($row['equipped'])
|
||||
{
|
||||
case'hand_a':
|
||||
$zweihander = ('weapon2h' == $item->type);
|
||||
$unit->count1 = 1;
|
||||
$unit->type1 = $item->damage_type;
|
||||
$unit->sp1_type = $item->special_type;
|
||||
$unit->sp1_param = $item->special_param;
|
||||
foreach($attackBonusKeys as $name)
|
||||
$modWpn1[$name] += $item->$name;
|
||||
break;
|
||||
case'hand_b':
|
||||
$unit->count2 = 1;
|
||||
$unit->type2 = $item->damage_type;
|
||||
$unit->sp2_type = $item->special_type;
|
||||
$unit->sp2_param = $item->special_param;
|
||||
foreach($attackBonusKeys as $name)
|
||||
$modWpn2[$name] += $item->$name;
|
||||
break;
|
||||
case'armor':
|
||||
$unit->armor_sp_type = $item->special_type;
|
||||
$unit->armor_sp_param = $item->special_param;
|
||||
//nobreak
|
||||
default:
|
||||
foreach($attackBonusKeys as $name)
|
||||
{
|
||||
$modWpn1[$name] += $item->$name;
|
||||
$modWpn2[$name] += $item->$name;
|
||||
}
|
||||
break;
|
||||
}
|
||||
foreach($armorBonusKeys as $name)
|
||||
$modArmor[$name] += $item->$name;
|
||||
}
|
||||
$unit->count1 = 1;
|
||||
$unit->count2 = $zweihander ? 0 : 1;
|
||||
//first hand
|
||||
$pstrSkill = $this->s_pstr;
|
||||
$mstrSkill = $this->s_mstr;
|
||||
if($zweihander)
|
||||
{
|
||||
$pstrSkill *= 1.7;
|
||||
$mstrSkill *= 1.7;
|
||||
}
|
||||
if('m' != $unit->type1)
|
||||
{
|
||||
$unit->atk1 = Daemon_Math::combatStat($this->a_dex, $modWpn1['patk_p'], $modWpn1['patk_c'], $this->s_patk);
|
||||
$unit->str1 = Daemon_Math::combatStat($this->a_str, $modWpn1['pstr_p'], $modWpn1['pstr_c'], $pstrSkill);
|
||||
}
|
||||
else
|
||||
{
|
||||
$unit->atk1 = Daemon_Math::combatStat($this->a_pwr, $modWpn1['matk_p'], $modWpn1['matk_c'], $this->s_matk);
|
||||
$unit->str1 = Daemon_Math::combatStat($this->a_pwr, $modWpn1['mstr_p'], $modWpn1['mstr_c'], $mstrSkill);
|
||||
}
|
||||
//second hand
|
||||
if('m' != $unit->type2)
|
||||
{
|
||||
$unit->atk2 = Daemon_Math::combatStat($this->a_dex, $modWpn2['patk_p'], $modWpn2['patk_c'], $this->s_patk);
|
||||
$unit->str2 = Daemon_Math::combatStat($this->a_str, $modWpn2['pstr_p'], $modWpn2['pstr_c'], $this->s_pstr);
|
||||
}
|
||||
else
|
||||
{
|
||||
$unit->atk2 = Daemon_Math::combatStat($this->a_pwr, $modWpn2['matk_p'], $modWpn2['matk_c'], $this->s_matk);
|
||||
$unit->str2 = Daemon_Math::combatStat($this->a_pwr, $modWpn2['mstr_p'], $modWpn2['mstr_c'], $this->s_mstr);
|
||||
}
|
||||
//physical defense
|
||||
$unit->pdef = Daemon_Math::combatStat($this->a_dex, $modArmor['pdef_p'], $modArmor['pdef_c'], $this->s_pdef);
|
||||
$unit->pres = Daemon_Math::combatStat($this->a_vit, $modArmor['pres_p'], $modArmor['pres_c'], $this->s_pres);
|
||||
//magical defense
|
||||
$unit->mdef = Daemon_Math::combatStat($this->a_wil, $modArmor['mdef_p'], $modArmor['mdef_c'], $this->s_mdef);
|
||||
$unit->mres = Daemon_Math::combatStat($this->a_wil, $modArmor['mres_p'], $modArmor['mres_c'], $this->s_mres);
|
||||
//armor & speed
|
||||
$unit->speed = Daemon_Math::combatStat($this->a_dex, $modArmor['speed'], 0, 0);
|
||||
$unit->armor = $modArmor['armor'];
|
||||
//regen
|
||||
$unit->regen = Daemon_Math::combatRegen($this->a_vit, $modArmor['regen'] + $this->s_preg);
|
||||
$unit->put();
|
||||
}
|
||||
|
||||
|
||||
//try to subtract the cost from character's gold, cancel the operation if the cost is too big
|
||||
public function payGold($cost, $bankEnabled)
|
||||
{
|
||||
$charGold = $this->gold_purse;
|
||||
if($bankEnabled)
|
||||
$charGold += $this->gold_bank;
|
||||
if($charGold < $cost)
|
||||
{
|
||||
Daemon_MsgQueue::add("Wymagane $cost zł - nie masz tyle złota.");
|
||||
return false;
|
||||
}
|
||||
$deltaPurse = min($cost, $this->gold_purse);
|
||||
$this->gold_purse -= $deltaPurse;
|
||||
$this->gold_bank -= $cost - $deltaPurse;
|
||||
$this->put();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//regenerates one-turn-worth of health & mana
|
||||
public function regen($resting)
|
||||
{
|
||||
$this->mana += $this->mana_regen;
|
||||
if($resting)
|
||||
{
|
||||
$this->health += $this->a_vit;
|
||||
$this->mana += ceil($this->a_pwr / 4);
|
||||
}
|
||||
if($this->health > $this->health_max)
|
||||
$this->health = $this->health_max;
|
||||
if($this->mana > $this->mana_max)
|
||||
$this->mana = $this->mana_max;
|
||||
}
|
||||
|
||||
|
||||
//calculates combat stats based on attributes, skills and equipment
|
||||
public function resetCombatStats()
|
||||
{
|
||||
//health
|
||||
$old = $this->health_max;
|
||||
$this->health_max = 3*$this->a_str + 7*$this->a_vit;
|
||||
$this->health += $this->health_max - $old;
|
||||
//mana
|
||||
$old = $this->mana_max;
|
||||
$this->mana_max = 3*$this->a_pwr + 2*$this->a_wil;
|
||||
$this->mana += $this->mana_max - $old;
|
||||
$this->mana_regen = Daemon_Math::manaRegen($this->a_wil, $this->s_mreg);
|
||||
//used xp
|
||||
$this->xp_used = 0;
|
||||
foreach(array_keys(Daemon_Dictionary::$characterAttributes) as $key)
|
||||
{
|
||||
$col = "a_$key";
|
||||
$this->xp_used += $this->$col * ($this->$col + 1) / 2;
|
||||
}
|
||||
foreach(array_keys(Daemon_Dictionary::$characterSkills) as $key)
|
||||
{
|
||||
$col = "s_$key";
|
||||
$this->xp_used += $this->$col * ($this->$col + 1) / 2;
|
||||
}
|
||||
//update combat stats
|
||||
$this->loadEquipmentBonuses();
|
||||
}
|
||||
|
||||
|
||||
//respawns in selected location
|
||||
public function respawn($locationId, $defaultRespawn)
|
||||
{
|
||||
$respawns = $this->getRespawns($defaultRespawn);
|
||||
if(!isset($respawns[$locationId]))
|
||||
{
|
||||
Daemon_MsgQueue::add('Wybrana lokacja nie jest dostępna.');
|
||||
return false;
|
||||
}
|
||||
$this->location_id = $locationId;
|
||||
$this->health = $this->health_max;
|
||||
$this->mana = 4 * $this->mana_regen;
|
||||
$this->resetCombatStats();
|
||||
$this->put();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//executes selected event, returns event log
|
||||
public function runEvent(Daemon_View $view)
|
||||
{
|
||||
$event = $this->getLocationEvent();
|
||||
//monster attack
|
||||
if(isset($event['monsterId']))
|
||||
{
|
||||
$combat = new Daemon_MonsterCombat();
|
||||
$combat->attachCharacterData($this);
|
||||
$combat->attachDbClient($this->_dbClient);
|
||||
$combat->execute($view, $event['monsterId']);
|
||||
//return log
|
||||
return $combat->getCombatLog();
|
||||
}
|
||||
//special event
|
||||
if(isset($event['eventId'], $event['params']))
|
||||
{
|
||||
$handler = new Daemon_Event();
|
||||
$handler->attachCharacterData($this);
|
||||
$handler->attachDbClient($this->_dbClient);
|
||||
$handler->execute($view, $event['eventId'], $event['params']);
|
||||
return $handler->getEventLog();
|
||||
}
|
||||
//no event
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
//updates character's health, location etc to represent death
|
||||
public function setDeath($clearEquipment)
|
||||
{
|
||||
$this->deaths += 1;
|
||||
$this->health = 0;
|
||||
$this->mana = 0;
|
||||
$this->xp_free = 0;
|
||||
$this->location_id = null;
|
||||
if($clearEquipment)
|
||||
{
|
||||
$this->gold_purse = 0;
|
||||
$sql = "DELETE FROM inventory WHERE character_id=:id
|
||||
AND status='inventory' AND NOT FIND_IN_SET('bound', flags)";
|
||||
$params = array('id' => $this->character_id);
|
||||
$this->_dbClient->query($sql, $params);
|
||||
}
|
||||
$this->resetCombatStats();
|
||||
}
|
||||
|
||||
|
||||
public function setLocationEvent(array $data)
|
||||
{
|
||||
$event = array();
|
||||
//monster attack
|
||||
if(isset($data['monsterId']))
|
||||
$event['monsterId'] = $data['monsterId'];
|
||||
//special event
|
||||
if(isset($data['eventId'], $data['params']))
|
||||
{
|
||||
$event['eventId'] = $data['eventId'];
|
||||
$event['params'] = $data['params'];
|
||||
}
|
||||
$this->location_event = json_encode($event);
|
||||
}
|
||||
}
|
91
2013/daemon/lib/daemon/dbobject/clan.php
Normal file
91
2013/daemon/lib/daemon/dbobject/clan.php
Normal file
|
@ -0,0 +1,91 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_Clan extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'clans';
|
||||
protected $_index = array('clan_id');
|
||||
public $clan_id;
|
||||
public $name;
|
||||
public $leader_id = null;
|
||||
public $description = null;
|
||||
|
||||
|
||||
//accept an invitation
|
||||
public function acceptCharacter($characterId, Daemon_Forum $forum)
|
||||
{
|
||||
$sql = "SELECT 1 FROM clan_invitations WHERE clan_id=:clanId AND character_id=:charId";
|
||||
$params = array('clanId' => $this->clan_id, 'charId' => $characterId);
|
||||
if($this->_dbClient->selectValue($sql, $params))
|
||||
{
|
||||
$sql = "UPDATE characters SET clan_id=:clanId WHERE character_id=:charId";
|
||||
$params = array('clanId' => $this->clan_id, 'charId' => $characterId);
|
||||
$this->_dbClient->query($sql, $params);
|
||||
$sql = "DELETE FROM clan_invitations WHERE character_id=:id";
|
||||
$this->_dbClient->query($sql, array('id' => $characterId));
|
||||
$msg = "Podanie do klanu $this->name zostało zaakceptowane.";
|
||||
$forum->addMailById(null, $characterId, $msg);
|
||||
}
|
||||
else Daemon_MsgQueue::add('Wybrane zaproszenie nie istnieje.');
|
||||
}
|
||||
|
||||
|
||||
//deletes clan and updates its members
|
||||
public function delete()
|
||||
{
|
||||
//TODO
|
||||
$params = array('id' => $this->clan_id);
|
||||
$sql = "DELETE FROM clans WHERE clan_id=:id";
|
||||
$this->_dbClient->query($sql, $params);
|
||||
$sql = "DELETE FROM clan_invitations WHERE clan_id=:id";
|
||||
$this->_dbClient->query($sql, $params);
|
||||
$sql = "UPDATE characters SET clan_id=NULL WHERE clan_id=:id";
|
||||
$this->_dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//reads a list of invitations
|
||||
public function getInvitations()
|
||||
{
|
||||
$sql = "SELECT i.*, c.name AS character_name, cd.level, cd.xp_used,
|
||||
cd.faction_id, COALESCE(cd.rank_id, 0) AS rank_id,
|
||||
date_format(c.date_created, '%Y-%m-%d') AS date_created
|
||||
FROM clan_invitations i JOIN characters c USING(character_id) JOIN character_data cd USING(character_id)
|
||||
WHERE i.clan_id=:id";
|
||||
return $this->_dbClient->selectAll($sql, array('id' => $this->clan_id));
|
||||
}
|
||||
|
||||
|
||||
//fetches leader's name
|
||||
public function getLeaderName()
|
||||
{
|
||||
$sql = "SELECT name FROM characters WHERE character_id=:id";
|
||||
return $this->_dbClient->selectValue($sql, array('id' => $this->leader_id));
|
||||
}
|
||||
|
||||
|
||||
//reads a list of members
|
||||
public function getMembers()
|
||||
{
|
||||
$sql = "SELECT cd.character_id, c.name, cd.level, cd.xp_used,
|
||||
cd.faction_id, COALESCE(cd.rank_id, 0) AS rank_id,
|
||||
date_format(c.date_created, '%Y-%m-%d') AS date_created
|
||||
FROM characters c JOIN character_data cd USING(character_id) WHERE c.clan_id=:id";
|
||||
$result = $this->_dbClient->selectAll($sql, array('id' => $this->clan_id));
|
||||
foreach($result as &$row)
|
||||
$row['_isLeader'] = ($row['character_id'] == $this->leader_id);
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
//removes member from clan
|
||||
public function kickMember($characterId, Daemon_Forum $forum)
|
||||
{
|
||||
if($characterId != $this->leader_id)
|
||||
{
|
||||
$sql = "UPDATE characters SET clan_id = NULL WHERE character_id=:id";
|
||||
$this->_dbClient->query($sql, array('id' => $characterId));
|
||||
$forum->addMailById(null, $characterId, 'Wyrzucono cię z klanu.');
|
||||
}
|
||||
else Daemon_MsgQueue::add('Przywódca nie może odejść, jedynie rozwiązać klan.');
|
||||
}
|
||||
}
|
63
2013/daemon/lib/daemon/dbobject/combatunit.php
Normal file
63
2013/daemon/lib/daemon/dbobject/combatunit.php
Normal file
|
@ -0,0 +1,63 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_CombatUnit extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'combat_units';
|
||||
protected $_index = array('combat_unit_id');
|
||||
public $combat_unit_id;
|
||||
public $name = null;
|
||||
public $faction_id = null;
|
||||
public $health = 70;
|
||||
public $health_max = 70;
|
||||
public $str1 = 7;
|
||||
public $atk1 = 7;
|
||||
public $type1 = 'p';
|
||||
public $count1 = 1;
|
||||
public $sp1_type = null;
|
||||
public $sp1_param = null;
|
||||
public $str2 = 7;
|
||||
public $atk2 = 7;
|
||||
public $type2 = null;
|
||||
public $count2 = 0;
|
||||
public $sp2_type = null;
|
||||
public $sp2_param = null;
|
||||
public $pdef = 7;
|
||||
public $pres = 7;
|
||||
public $mdef = 7;
|
||||
public $mres = 7;
|
||||
public $speed = 7;
|
||||
public $armor = 0;
|
||||
public $armor_sp_type = null;
|
||||
public $armor_sp_param = null;
|
||||
public $regen = 0;
|
||||
//special property types
|
||||
const SP_ANTIPOISON = 'antipoison';
|
||||
const SP_ANTIVAMP = 'antivamp';
|
||||
const SP_BLOODY = 'bloody';
|
||||
const SP_DEMON = 'demon';
|
||||
const SP_ETHER = 'ether';
|
||||
const SP_FACTION = 'faction';
|
||||
const SP_POISON = 'poison';
|
||||
const SP_SHOCK = 'shock';
|
||||
const SP_STUN = 'stun';
|
||||
const SP_SWARM = 'swarm';
|
||||
const SP_VAMPIRE = 'vampiric';
|
||||
|
||||
|
||||
public function validate()
|
||||
{
|
||||
$attackTypes = Daemon_Dictionary::$combatAttackTypes;
|
||||
$attackSpecials = Daemon_Dictionary::$combatAttackSpecials;
|
||||
$armorSpecials = Daemon_Dictionary::$combatArmorSpecials;
|
||||
if (!isset($attackTypes[$this->type1]))
|
||||
$this->type1 = null;
|
||||
if (!isset($attackTypes[$this->type2]))
|
||||
$this->type2 = null;
|
||||
if (!isset($attackSpecials[$this->sp1_type]))
|
||||
$this->sp1_type = null;
|
||||
if (!isset($attackSpecials[$this->sp2_type]))
|
||||
$this->sp2_type = null;
|
||||
if (!isset($armorSpecials[$this->armor_sp_type]))
|
||||
$this->armor_sp_type = null;
|
||||
}
|
||||
}
|
11
2013/daemon/lib/daemon/dbobject/event.php
Normal file
11
2013/daemon/lib/daemon/dbobject/event.php
Normal file
|
@ -0,0 +1,11 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_Event extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'events';
|
||||
protected $_index = array('event_id');
|
||||
public $event_id;
|
||||
public $name;
|
||||
public $handle = null;
|
||||
public $description = null;
|
||||
}
|
160
2013/daemon/lib/daemon/dbobject/item.php
Normal file
160
2013/daemon/lib/daemon/dbobject/item.php
Normal file
|
@ -0,0 +1,160 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_Item extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'items';
|
||||
protected $_index = array('item_id');
|
||||
public $item_id;
|
||||
public $name;
|
||||
public $type = 'item';
|
||||
public $value = 1, $suggested_value = 0.0;
|
||||
public $damage_type = null;
|
||||
public $special_type = null;
|
||||
public $special_param = null;
|
||||
public $pstr_p = 0, $pstr_c = 0, $patk_p = 0, $patk_c = 0;
|
||||
public $pdef_p = 0, $pdef_c = 0, $pres_p = 0, $pres_c = 0;
|
||||
public $mstr_p = 0, $mstr_c = 0, $matk_p = 0, $matk_c = 0;
|
||||
public $mdef_p = 0, $mdef_c = 0, $mres_p = 0, $mres_c = 0;
|
||||
public $armor = 0, $speed = 0, $regen = 0.0;
|
||||
public $description = null;
|
||||
|
||||
|
||||
//generates a readable description
|
||||
public function getDescription()
|
||||
{
|
||||
$itemTypes = Daemon_Dictionary::$itemTypes;
|
||||
$itemWeaponTypes = Daemon_Dictionary::$itemWeaponTypes;
|
||||
$itemDamageTypes = Daemon_Dictionary::$itemDamageTypes;
|
||||
$itemArmorTypes = Daemon_Dictionary::$itemArmorTypes;
|
||||
$combatAttackSpecials = Daemon_Dictionary::$combatAttackSpecials;
|
||||
$combatArmorSpecials = Daemon_Dictionary::$combatArmorSpecials;
|
||||
//item type
|
||||
$typeName = $specialName = null;
|
||||
if (!empty($itemWeaponTypes[$this->type]))
|
||||
{
|
||||
if ($this->damage_type && isset($itemDamageTypes[$this->damage_type]))
|
||||
{
|
||||
$typeName = sprintf('broń %s (obrażenia %s)',
|
||||
$itemWeaponTypes[$this->type], $itemDamageTypes[$this->damage_type]);
|
||||
}
|
||||
else
|
||||
$typeName = 'tarcza';
|
||||
if(isset($combatAttackSpecials[$this->special_type]))
|
||||
$specialName = sprintf('%s (%s)', $combatAttackSpecials[$this->special_type], $this->special_param);
|
||||
}
|
||||
elseif (!empty($itemArmorTypes[$this->type]))
|
||||
{
|
||||
$typeName = $itemArmorTypes[$this->type];
|
||||
if(isset($combatArmorSpecials[$this->special_type]))
|
||||
$specialName = sprintf('%s (%s)', $combatArmorSpecials[$this->special_type], $this->special_param);
|
||||
}
|
||||
else //usables
|
||||
{
|
||||
$typeName = 'niezakładalny';
|
||||
}
|
||||
//stats
|
||||
$stats = array();
|
||||
if($specialName)
|
||||
$stats[] = $specialName;
|
||||
if('item' != $this->type)
|
||||
{
|
||||
if($this->pstr_p || $this->pstr_c)
|
||||
$stats[] = $this->getStatDescription('pstr', $this->pstr_p, $this->pstr_c);
|
||||
if($this->patk_p || $this->patk_c)
|
||||
$stats[] = $this->getStatDescription('patk', $this->patk_p, $this->patk_c);
|
||||
if($this->pdef_p || $this->pdef_c)
|
||||
$stats[] = $this->getStatDescription('pdef', $this->pdef_p, $this->pdef_c);
|
||||
if($this->pres_p || $this->pres_c)
|
||||
$stats[] = $this->getStatDescription('pres', $this->pres_p, $this->pres_c);
|
||||
if($this->mstr_p || $this->mstr_c)
|
||||
$stats[] = $this->getStatDescription('mstr', $this->mstr_p, $this->mstr_c);
|
||||
if($this->matk_p || $this->matk_c)
|
||||
$stats[] = $this->getStatDescription('matk', $this->matk_p, $this->matk_c);
|
||||
if($this->mdef_p || $this->mdef_c)
|
||||
$stats[] = $this->getStatDescription('mdef', $this->mdef_p, $this->mdef_c);
|
||||
if($this->mres_p || $this->mres_c)
|
||||
$stats[] = $this->getStatDescription('mres', $this->mres_p, $this->mres_c);
|
||||
if($this->armor)
|
||||
$stats[] = sprintf('pancerz%+d', $this->armor);
|
||||
if($this->speed)
|
||||
$stats[] = sprintf('szybkość%+d%%', $this->speed);
|
||||
if($this->regen)
|
||||
$stats[] = sprintf('regen%+d', $this->regen);
|
||||
}
|
||||
//final concatenation
|
||||
if($stats)
|
||||
$desc = sprintf('%s; %s', $typeName, implode(', ', $stats));
|
||||
else $desc = $typeName;
|
||||
return $desc;
|
||||
}
|
||||
|
||||
|
||||
//returns a list of matching equipment slots
|
||||
public function getSlots()
|
||||
{
|
||||
if ($this->type == 'weapon1h')
|
||||
return array('hand_a', 'hand_b');
|
||||
elseif ($this->type == 'weapon2h')
|
||||
return array('hand_a');
|
||||
elseif ($this->type == 'accesory')
|
||||
return array('accesory_a', 'accesory_b');
|
||||
elseif ($this->type != 'item')
|
||||
return array($this->type);
|
||||
else return array();
|
||||
}
|
||||
|
||||
|
||||
private function getStatDescription($name, $value_p = 0, $value_c = 0)
|
||||
{
|
||||
$result = $name;
|
||||
if($value_p)
|
||||
$result .= sprintf('%+d%%', $value_p);
|
||||
if($value_c)
|
||||
$result .= sprintf('%+d', $value_c);
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
public function updateSuggestedValue(Daemon_DbConfig $dbCfg)
|
||||
{
|
||||
if ($this->type == 'item')
|
||||
return;
|
||||
$this->suggested_value = 0.0;
|
||||
$baseValue = $dbCfg->generatorBaseValue;
|
||||
$weights = $dbCfg->getGeneratorWeights($this->type);
|
||||
foreach ($weights as $key => $val)
|
||||
{
|
||||
if (isset($this->$key))
|
||||
$this->suggested_value += $this->$key * $val;
|
||||
}
|
||||
$this->suggested_value *= $baseValue;
|
||||
}
|
||||
|
||||
|
||||
public function validate()
|
||||
{
|
||||
if ($this->type == 'weapon1h' || $this->type == 'weapon2h')
|
||||
{
|
||||
$specials = Daemon_Dictionary::$combatAttackSpecials;
|
||||
if(!isset($specials[$this->special_type]))
|
||||
{
|
||||
$this->special_type = null;
|
||||
$this->special_param = null;
|
||||
}
|
||||
}
|
||||
elseif ($this->type != 'item')
|
||||
{
|
||||
$this->damage_type = null;
|
||||
$specials = Daemon_Dictionary::$combatArmorSpecials;
|
||||
if(($this->type != 'armor') || !isset($specials[$this->special_type]))
|
||||
{
|
||||
$this->special_type = null;
|
||||
$this->special_param = null;
|
||||
}
|
||||
}
|
||||
else //usables
|
||||
{
|
||||
$this->damage_type = null;
|
||||
}
|
||||
}
|
||||
}
|
20
2013/daemon/lib/daemon/dbobject/itemtemplate.php
Normal file
20
2013/daemon/lib/daemon/dbobject/itemtemplate.php
Normal file
|
@ -0,0 +1,20 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_ItemTemplate extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'item_templates';
|
||||
protected $_index = array('id');
|
||||
public $id;
|
||||
public $name;
|
||||
public $pstr_p_p = 1, $pstr_p_m = 1, $pstr_c_p = 1, $pstr_c_m = 1;
|
||||
public $patk_p_p = 1, $patk_p_m = 1, $patk_c_p = 1, $patk_c_m = 1;
|
||||
public $pdef_p_p = 1, $pdef_p_m = 1, $pdef_c_p = 1, $pdef_c_m = 1;
|
||||
public $pres_p_p = 1, $pres_p_m = 1, $pres_c_p = 1, $pres_c_m = 1;
|
||||
public $mstr_p_p = 1, $mstr_p_m = 1, $mstr_c_p = 1, $mstr_c_m = 1;
|
||||
public $matk_p_p = 1, $matk_p_m = 1, $matk_c_p = 1, $matk_c_m = 1;
|
||||
public $mdef_p_p = 1, $mdef_p_m = 1, $mdef_c_p = 1, $mdef_c_m = 1;
|
||||
public $mres_p_p = 1, $mres_p_m = 1, $mres_c_p = 1, $mres_c_m = 1;
|
||||
public $armor_p = 1, $armor_m = 1;
|
||||
public $speed_p = 1, $speed_m = 1;
|
||||
public $regen_p = 1, $regen_m = 1;
|
||||
}
|
303
2013/daemon/lib/daemon/dbobject/location.php
Normal file
303
2013/daemon/lib/daemon/dbobject/location.php
Normal file
|
@ -0,0 +1,303 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_Location extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'locations';
|
||||
protected $_index = array('location_id');
|
||||
public $location_id;
|
||||
public $name;
|
||||
public $type = 'normal';
|
||||
public $chance1 = 1, $chance2 = 1;
|
||||
public $region_id = null;
|
||||
public $faction_id = null;
|
||||
public $description = null;
|
||||
public $picture_url = null;
|
||||
private $_characterData = null;
|
||||
|
||||
|
||||
//spends one turn on hunting
|
||||
public function actionHunt()
|
||||
{
|
||||
//check turn costs
|
||||
if(!$this->_characterData->checkTurnCosts())
|
||||
return false;
|
||||
//update character data
|
||||
$this->_characterData->regen(false);
|
||||
//check for events
|
||||
$this->checkEvents(2);
|
||||
//save character data
|
||||
$this->_characterData->put();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//spends one turn on resting
|
||||
public function actionRest()
|
||||
{
|
||||
//check turn costs
|
||||
if(!$this->_characterData->checkTurnCosts())
|
||||
return false;
|
||||
//update character data
|
||||
$this->_characterData->regen(true);
|
||||
//check for events
|
||||
$this->checkEvents(1);
|
||||
//save character data
|
||||
$this->_characterData->put();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//spends one turn on training
|
||||
public function actionTrain()
|
||||
{
|
||||
//check turn costs
|
||||
if(!$this->_characterData->checkTurnCosts())
|
||||
return false;
|
||||
//update character data
|
||||
$this->_characterData->regen(false);
|
||||
$this->_characterData->xp_free += 1;
|
||||
//check for events
|
||||
$this->checkEvents(1);
|
||||
//save character data
|
||||
$this->_characterData->put();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//moves character to specified location
|
||||
public function actionTravel($destinationId)
|
||||
{
|
||||
//read path data
|
||||
$sql = "SELECT * FROM location_paths WHERE location_id=:id AND destination_id=:destId";
|
||||
$params = array('id' => $this->location_id, 'destId' => $destinationId);
|
||||
$path = $this->_dbClient->selectRow($sql, $params);
|
||||
if(!$path)
|
||||
{
|
||||
Daemon_MsgQueue::add('Wybrana ścieżka jest niedostępna.');
|
||||
return false;
|
||||
}
|
||||
//check turn costs
|
||||
if(!$this->_characterData->checkTurnCosts($path['cost_gold'], $path['cost_mana']))
|
||||
return false;
|
||||
//update character data
|
||||
$this->_characterData->regen(false);
|
||||
$this->_characterData->location_id = $destinationId;
|
||||
//load destination
|
||||
$this->get(array('location_id' => $destinationId));
|
||||
if($this->region_id)
|
||||
{
|
||||
$sql = "INSERT IGNORE INTO character_regions (character_id, region_id) VALUES (:charId, :regionId)";
|
||||
$params = array('charId' => $this->_characterData->character_id, 'regionId' => $this->region_id);
|
||||
$this->_dbClient->query($sql, $params);
|
||||
}
|
||||
//check for events
|
||||
$this->checkEvents(1);
|
||||
//save character data
|
||||
$this->_characterData->put();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
public function attachCharacterData(Daemon_DbObject_CharacterData $characterData)
|
||||
{
|
||||
$this->_characterData = $characterData;
|
||||
}
|
||||
|
||||
|
||||
//checks for events in a location
|
||||
private function checkEvents($chanceMult)
|
||||
{
|
||||
$event = false;
|
||||
$eventParams = array();
|
||||
//check if there was any event
|
||||
if($this->chance2)
|
||||
{
|
||||
$d256 = mt_rand(0, 255);
|
||||
$failChance = 256 * (1 - $this->chance1 / $this->chance2);
|
||||
$chance = $chanceMult ? (256 - $failChance / $chanceMult) : 0;
|
||||
$event = ($d256 < $chance);
|
||||
}
|
||||
//check event type
|
||||
if($event)
|
||||
{
|
||||
//read monster data
|
||||
$sql = "SELECT * FROM location_monsters WHERE location_id=:id";
|
||||
$monsters = $this->_dbClient->selectAll($sql, array('id' => $this->location_id));
|
||||
//read special events
|
||||
$sql = "SELECT * FROM location_events WHERE location_id=:id";
|
||||
$events = $this->_dbClient->selectAll($sql, array('id' => $this->location_id));
|
||||
//find event data
|
||||
$chanceSum = 0;
|
||||
foreach($monsters as $row)
|
||||
$chanceSum += $row['chance'];
|
||||
foreach($events as $row)
|
||||
$chanceSum += $row['chance'];
|
||||
$d256 = mt_rand(0, 255);
|
||||
foreach($monsters as $row)
|
||||
{
|
||||
$chance = 256 * $row['chance'] / $chanceSum;
|
||||
if($d256 < $chance)
|
||||
{
|
||||
$eventParams = array('monsterId' => $row['monster_id']);
|
||||
break;
|
||||
}
|
||||
$d256 -= $chance;
|
||||
}
|
||||
foreach($events as $row)
|
||||
{
|
||||
$chance = 256 * $row['chance'] / $chanceSum;
|
||||
if($d256 < $chance)
|
||||
{
|
||||
$eventParams = array('eventId' => $row['event_id'], 'params' => $row['params']);
|
||||
break;
|
||||
}
|
||||
$d256 -= $chance;
|
||||
}
|
||||
}
|
||||
//store event
|
||||
if(!$eventParams)
|
||||
Daemon_MsgQueue::add('Brak zdarzeń w tej turze.');
|
||||
$this->_characterData->setLocationEvent($eventParams);
|
||||
}
|
||||
|
||||
|
||||
//counts characters present in a location
|
||||
public function getCharacterCount($limit)
|
||||
{
|
||||
$sql = "SELECT COUNT(1) FROM character_data WHERE location_id=:id LIMIT :limit";
|
||||
$params = array('id' => $this->location_id, 'limit' => $limit);
|
||||
return $this->_dbClient->selectValue($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//gets a list of characters present in a location
|
||||
public function getCharacters(Daemon_DbObject_CharacterData $char, $halfLimit = null)
|
||||
{
|
||||
if(empty($this->location_id))
|
||||
return array();
|
||||
$sql = "SELECT MAX(rollover_id) FROM rollovers";
|
||||
$rolloverId = $this->_dbClient->selectValue($sql);
|
||||
$charId = $this->_characterData->character_id;
|
||||
$cols = "c.character_id, c.name, cp.location_id, cp.level, cp.xp_used,
|
||||
c.clan_id, cp.faction_id, COALESCE(cp.rank_id, 0) AS rank_id, f.name AS faction_name";
|
||||
$tables = "character_data cp
|
||||
JOIN characters c USING(character_id)
|
||||
LEFT JOIN factions f USING(faction_id)";
|
||||
$params = array('id' => $this->location_id, 'charId' => $charId);
|
||||
if($halfLimit)
|
||||
{
|
||||
$params['xp'] = $char->xp_used;
|
||||
$params['halfLimit'] = $halfLimit;
|
||||
$sql = "(
|
||||
SELECT $cols FROM $tables
|
||||
WHERE cp.location_id=:id AND cp.character_id!=:charId AND cp.xp_used >= :xp
|
||||
ORDER BY xp_used ASC LIMIT $halfLimit
|
||||
) UNION (
|
||||
SELECT $cols FROM $tables
|
||||
WHERE cp.location_id=:id AND cp.character_id!=:charId AND cp.xp_used <= :xp
|
||||
ORDER BY xp_used DESC LIMIT $halfLimit
|
||||
) ORDER BY xp_used DESC, name ASC";
|
||||
}
|
||||
else
|
||||
{
|
||||
$sql = "SELECT $cols FROM $tables
|
||||
WHERE cp.location_id=:id AND cp.character_id!=:charId
|
||||
ORDER BY cp.xp_used DESC, c.name ASC";
|
||||
}
|
||||
$data = $this->_dbClient->selectAll($sql, $params);
|
||||
foreach($data as &$row)
|
||||
{
|
||||
$row['_canAttack'] = $char->canAttack($row, $rolloverId, false);
|
||||
$row['_sparring'] = ('normal' != $char->getCombatType($row, $this->type));
|
||||
}
|
||||
return $data;
|
||||
}
|
||||
|
||||
|
||||
//gets the name of a faction owning location/caern
|
||||
public function getFactionName()
|
||||
{
|
||||
if(empty($this->faction_id))
|
||||
return null;
|
||||
$sql = "SELECT name FROM factions WHERE faction_id=:id";
|
||||
return $this->_dbClient->selectValue($sql, array('id' => $this->faction_id));
|
||||
}
|
||||
|
||||
|
||||
//get a full list of maps
|
||||
public function getMaps()
|
||||
{
|
||||
$sql = "SELECT * FROM maps WHERE url IS NOT NULL AND url != '' ORDER BY sort, name";
|
||||
return $this->_dbClient->selectAll($sql, array());
|
||||
}
|
||||
|
||||
|
||||
//get a list of paths starting in current location
|
||||
public function getPaths()
|
||||
{
|
||||
if(empty($this->location_id))
|
||||
return array();
|
||||
$sql = "SELECT p.*, IF(p.name IS NULL OR p.name='', l.name, p.name) AS path_name,
|
||||
(p.cost_gold<=:gold AND p.cost_mana<=:mana) AS _enabled
|
||||
FROM location_paths p JOIN locations l ON p.destination_id=l.location_id
|
||||
WHERE p.location_id=:id ORDER BY l.name, l.location_id";
|
||||
$params = array('id' => $this->location_id,
|
||||
'gold' => $this->_characterData->gold_purse,
|
||||
'mana' => $this->_characterData->mana,
|
||||
);
|
||||
return $this->_dbClient->selectAll($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
public function getPictureUrl()
|
||||
{
|
||||
if ($this->picture_url)
|
||||
return $this->picture_url;
|
||||
$sql = "SELECT picture_url FROM regions WHERE region_id=:id";
|
||||
return $this->_dbClient->selectValue($sql, array('id' => $this->region_id));
|
||||
}
|
||||
|
||||
|
||||
//get name of the location's region
|
||||
public function getRegionName()
|
||||
{
|
||||
if(empty($this->region_id))
|
||||
return null;
|
||||
$sql = "SELECT name FROM regions WHERE region_id=:id";
|
||||
return $this->_dbClient->selectValue($sql, array('id' => $this->region_id));
|
||||
}
|
||||
|
||||
|
||||
//get a list of available services
|
||||
public function getServices()
|
||||
{
|
||||
if(empty($this->location_id))
|
||||
return array();
|
||||
$sql = "SELECT s.*, (
|
||||
(s.faction_id IS NULL OR :factionId IS NULL OR s.faction_id = :factionId)
|
||||
AND (s.rank_id IS NULL OR s.rank_id <= :rankId)
|
||||
) AS _enabled
|
||||
FROM location_services l JOIN services s USING(service_id)
|
||||
WHERE l.location_id=:id ORDER BY s.name";
|
||||
$params = array('id' => $this->location_id,
|
||||
'factionId' => $this->_characterData->faction_id,
|
||||
'rankId' => $this->_characterData->rank_id,
|
||||
);
|
||||
return $this->_dbClient->selectAll($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//checks object data
|
||||
public function validate()
|
||||
{
|
||||
$this->chance1 = max(0, (int) $this->chance1);
|
||||
$this->chance2 = max(1, (int) $this->chance2);
|
||||
if($this->type != 'boss')
|
||||
{
|
||||
$this->boss_id = null;
|
||||
$this->boss_status = null;
|
||||
if ($this->type != 'caern')
|
||||
$this->faction_id = null;
|
||||
}
|
||||
}
|
||||
}
|
49
2013/daemon/lib/daemon/dbobject/monster.php
Normal file
49
2013/daemon/lib/daemon/dbobject/monster.php
Normal file
|
@ -0,0 +1,49 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_DbObject_Monster extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'monsters';
|
||||
protected $_index = array('monster_id');
|
||||
public $monster_id;
|
||||
public $name;
|
||||
public $class = 1;
|
||||
public $level = 1;
|
||||
public $gold = 0;
|
||||
public $chance1 = 1;
|
||||
public $chance2 = 1;
|
||||
public $title_id = null;
|
||||
public $combat_unit_id = null;
|
||||
private $_combatUnit;
|
||||
|
||||
|
||||
//returns Daemon_DbObject_CombatUnit instance
|
||||
public function getCombatUnit($full = false)
|
||||
{
|
||||
if(!$this->_combatUnit)
|
||||
{
|
||||
$this->_combatUnit = $full ? new Daemon_Combat_Unit() : new Daemon_DbObject_CombatUnit();
|
||||
$this->_combatUnit->attachDbClient($this->_dbClient);
|
||||
if($this->combat_unit_id)
|
||||
$this->_combatUnit->get(array('combat_unit_id' => $this->combat_unit_id));
|
||||
$this->_combatUnit->name = $this->name;
|
||||
$this->_combatUnit->faction_id = null;
|
||||
}
|
||||
return $this->_combatUnit;
|
||||
}
|
||||
|
||||
|
||||
public function validate()
|
||||
{
|
||||
$this->class = max(0, (int) $this->class);
|
||||
$this->level = max(0, (int) $this->level);
|
||||
$this->gold = max(0, (int) $this->gold);
|
||||
$this->chance1 = max(0, (int) $this->chance1);
|
||||
$this->chance2 = max(1, (int) $this->chance2);
|
||||
//set class
|
||||
foreach (Daemon_Dictionary::$monsterClassLevels as $class => $level)
|
||||
{
|
||||
if ($this->level > $level)
|
||||
$this->class = $class;
|
||||
}
|
||||
}
|
||||
}
|
387
2013/daemon/lib/daemon/dbobject/player.php
Normal file
387
2013/daemon/lib/daemon/dbobject/player.php
Normal file
|
@ -0,0 +1,387 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//manages player data, authentication and character list
|
||||
class Daemon_DbObject_Player extends Daemon_DbObject
|
||||
{
|
||||
protected $_tableName = 'players';
|
||||
protected $_index = array('player_id');
|
||||
public $player_id;
|
||||
public $login;
|
||||
public $password;
|
||||
public $roles;
|
||||
public $name;
|
||||
public $date_created;
|
||||
public $last_login;
|
||||
public $skin;
|
||||
public $email;
|
||||
//session settings
|
||||
const SESSION_TIMEOUT = 900; //seconds
|
||||
const VARNAME_CHARACTER_ID = 'characterId';
|
||||
const VARNAME_PLAYER_ID = 'playerId';
|
||||
const VARNAME_PLAYER_ADDR = 'playerAddr';
|
||||
const VARNAME_TIMESTAMP = 'lastAction';
|
||||
|
||||
|
||||
public function __construct(Daemon_DbClient $dbClient)
|
||||
{
|
||||
parent::__construct();
|
||||
$this->attachDbClient($dbClient);
|
||||
$this->checkSession();
|
||||
if($id = $this->getPlayerId())
|
||||
parent::get(array('player_id' => $id));
|
||||
}
|
||||
|
||||
|
||||
//creates a new character
|
||||
public function addCharacter($name, $gender, $turnDelta, $turnLimit)
|
||||
{
|
||||
if(!$this->getPlayerId())
|
||||
return false;
|
||||
$maxLength = $this->_dbClient->getColumnMaxLength('characters', 'name');
|
||||
$name = Daemon::normalizeString($name, false);
|
||||
$gender = Daemon::normalizeString($gender, false);
|
||||
$validName = $this->validateName($name, $maxLength);
|
||||
$validGender = $this->validateGender($gender);
|
||||
if($validName && $validGender)
|
||||
{
|
||||
$sql = "INSERT INTO characters (player_id, name, gender, last_action) VALUES (:playerId, :name, :gender, now())";
|
||||
$params = array(
|
||||
'playerId' => $this->getPlayerId(),
|
||||
'name' => $name, 'gender' => $gender,
|
||||
);
|
||||
$this->_dbClient->query($sql, $params, 'Wybrane imię jest już zajęte.');
|
||||
if($id = $this->_dbClient->lastInsertId())
|
||||
{
|
||||
$turns = $this->getStartingTurns($turnDelta, $turnLimit);
|
||||
$sql = "INSERT INTO character_data(character_id, turns) VALUES (:id, :turns)";
|
||||
$this->_dbClient->query($sql, array('id' => $id, 'turns' => $turns));
|
||||
$sql = "INSERT INTO character_statistics(character_id) VALUES (:id)";
|
||||
$this->_dbClient->query($sql, array('id' => $id));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//checks and stores authentication data (logs in)
|
||||
public function authenticate($login, $password)
|
||||
{
|
||||
$this->get(array('login' => $login));
|
||||
if($this->player_id)
|
||||
{
|
||||
//check password
|
||||
list($salt, $hash) = explode(':', $this->password.':');
|
||||
if($hash == Daemon::passwordHash($salt, $password))
|
||||
{
|
||||
session_regenerate_id(true);
|
||||
$_SESSION[self::VARNAME_PLAYER_ID] = (int) $this->player_id;
|
||||
$_SESSION[self::VARNAME_PLAYER_ADDR] = getenv('REMOTE_ADDR');
|
||||
$_SESSION[self::VARNAME_TIMESTAMP] = time();
|
||||
$this->last_login = $this->_dbClient->selectValue("SELECT NOW()");
|
||||
$this->put();
|
||||
}
|
||||
else $this->player_id = null;
|
||||
}
|
||||
if(!$this->player_id)
|
||||
{
|
||||
Daemon_MsgQueue::add('Nieprawidłowy login lub hasło.');
|
||||
$this->unauthenticate();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//compares request data with stored auth data
|
||||
private function checkSession()
|
||||
{
|
||||
$prevAddr = $currentAddr = getenv('REMOTE_ADDR');
|
||||
$prevTime = $currentTime = time();
|
||||
if(isset($_SESSION[self::VARNAME_PLAYER_ADDR]))
|
||||
$prevAddr = $_SESSION[self::VARNAME_PLAYER_ADDR];
|
||||
if(isset($_SESSION[self::VARNAME_TIMESTAMP]))
|
||||
$prevTime = $_SESSION[self::VARNAME_TIMESTAMP];
|
||||
$validAddr = ($currentAddr == $prevAddr);
|
||||
$validTime = ($currentTime < $prevTime + self::SESSION_TIMEOUT);
|
||||
if($validAddr && $validTime)
|
||||
$_SESSION[self::VARNAME_TIMESTAMP] = $currentTime;
|
||||
else $this->unauthenticate();
|
||||
}
|
||||
|
||||
|
||||
//resets or deletes selected character
|
||||
public function deleteCharacter($characterId, $reset, $turnDelta, $turnLimit)
|
||||
{
|
||||
if(!$this->getPlayerId())
|
||||
return false;
|
||||
$sql = "SELECT character_id FROM characters WHERE character_id=:id AND player_id=:playerId";
|
||||
$params = array('id' => $characterId, 'playerId' => $this->getPlayerId());
|
||||
if($id = $this->_dbClient->selectValue($sql, $params))
|
||||
{
|
||||
$params = array('id' => $characterId);
|
||||
$tables = array('character_data', 'character_missions', 'character_regions',
|
||||
'character_statistics', 'character_titles', 'inventory');
|
||||
foreach($tables as $table)
|
||||
{
|
||||
$sql = "DELETE FROM $table WHERE character_id=:id";
|
||||
if ($table == 'character_titles')
|
||||
$sql .= " AND title_id NOT IN (SELECT title_id FROM titles WHERE type='special')";
|
||||
$this->_dbClient->query($sql, $params);
|
||||
}
|
||||
if ($reset)
|
||||
{
|
||||
$turns = $this->getStartingTurns($turnDelta, $turnLimit);
|
||||
$sql = "INSERT INTO character_data(character_id, turns) VALUES (:id, :turns)";
|
||||
$this->_dbClient->query($sql, array('id' => $id, 'turns' => $turns));
|
||||
$sql = "INSERT INTO character_statistics(character_id) VALUES (:id)";
|
||||
$this->_dbClient->query($sql, array('id' => $id));
|
||||
}
|
||||
else
|
||||
{
|
||||
$sql = "DELETE FROM characters WHERE character_id=:id";
|
||||
$this->_dbClient->query($sql, $params);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//returns basic data of active character
|
||||
public function getActiveCharacter()
|
||||
{
|
||||
$char = new Daemon_DbObject_Character;
|
||||
$char->attachDbClient($this->_dbClient);
|
||||
if($id = $this->getCharacterId())
|
||||
$char->get(array('character_id' => $id));
|
||||
$this->setCharacterId($char->character_id);
|
||||
$char->attachPlayer($this);
|
||||
return $char;
|
||||
}
|
||||
|
||||
|
||||
//returns active character's ID
|
||||
public function getCharacterId()
|
||||
{
|
||||
if(isset($_SESSION[self::VARNAME_CHARACTER_ID]))
|
||||
return $_SESSION[self::VARNAME_CHARACTER_ID];
|
||||
else return null;
|
||||
}
|
||||
|
||||
|
||||
//returns a list of player's characters
|
||||
public function getCharacters()
|
||||
{
|
||||
$sql = "SELECT c.character_id, c.name,
|
||||
cp.level, cp.turns, cp.health, cp.health_max, l.name AS location_name
|
||||
FROM characters c
|
||||
LEFT JOIN character_data cp USING(character_id)
|
||||
LEFT JOIN locations l USING(location_id)
|
||||
WHERE player_id = :playerId";
|
||||
$params = array('playerId' => $this->getPlayerId());
|
||||
$result = array();
|
||||
foreach((array) $this->_dbClient->selectAll($sql, $params) as $row)
|
||||
$result[$row['character_id']] = $row;
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
//returns authenticated player's ID
|
||||
public function getPlayerId()
|
||||
{
|
||||
if(isset($_SESSION[self::VARNAME_PLAYER_ID]))
|
||||
$this->player_id = $_SESSION[self::VARNAME_PLAYER_ID];
|
||||
else $this->player_id = null;
|
||||
return $this->player_id;
|
||||
}
|
||||
|
||||
|
||||
//returns a list of player's access roles
|
||||
public function getRoles()
|
||||
{
|
||||
if(!$id = $this->getPlayerId())
|
||||
return array();
|
||||
if(!is_array($this->roles))
|
||||
{
|
||||
$sql = "SELECT roles FROM players WHERE player_id=:playerId";
|
||||
$params = array('playerId' => $this->getPlayerId());
|
||||
$this->roles = explode(',', (string) $this->_dbClient->selectValue($sql, $params));
|
||||
}
|
||||
return $this->roles;
|
||||
}
|
||||
|
||||
|
||||
protected function getStartingTurns($turnDelta, $turnLimit)
|
||||
{
|
||||
$sql = "SELECT COUNT(rollover_id) FROM rollovers";
|
||||
$n = (int) $this->_dbClient->selectValue($sql);
|
||||
return min($turnLimit, $turnDelta * (1 + $n));
|
||||
}
|
||||
|
||||
|
||||
//checks if player has selected access role
|
||||
public function hasRole($name)
|
||||
{
|
||||
return in_array($name, $this->getRoles());
|
||||
}
|
||||
|
||||
|
||||
//stores a new password and sends mail with reset key
|
||||
public function preparePasswordReset($login, $email, $password, $passwordCopy)
|
||||
{
|
||||
if (!$this->validatePassword($password, $passwordCopy))
|
||||
return false;
|
||||
if (!$login || !$email)
|
||||
{
|
||||
Daemon_MsgQueue::add('Musisz podać login oraz email.');
|
||||
return false;
|
||||
}
|
||||
//validate login+email
|
||||
$sql = "SELECT player_id FROM players WHERE login=:login AND email=:email";
|
||||
$params = array('login' => $login, 'email' => $email);
|
||||
$playerId = $this->_dbClient->selectValue($sql, $params);
|
||||
if (!$playerId)
|
||||
{
|
||||
Daemon_MsgQueue::add('Nieprawidłowy login lub hasło.');
|
||||
return false;
|
||||
}
|
||||
//store password
|
||||
$key = sha1(Daemon::passwordSalt() . $login . $email);
|
||||
$salt = Daemon::passwordSalt();
|
||||
$passwordSql = sprintf('%s:%s', $salt, Daemon::passwordHash($salt, $password));
|
||||
$sql = "UPDATE players SET reset_key = :key, reset_password = :password,
|
||||
reset_until = now() + INTERVAL 1 WEEK WHERE player_id = :id";
|
||||
$params = array('id' => $playerId, 'key' => $key, 'password' => $passwordSql);
|
||||
$ok = $this->_dbClient->query($sql, $params);
|
||||
if (!$ok)
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie udało się zapisać nowego hasła.');
|
||||
return false;
|
||||
}
|
||||
//send mail
|
||||
$url = sprintf('%sreset-password?key=%s', $GLOBALS['cfg']->applicationUrl, $key);
|
||||
$subject = "Daemon 2: reset hasla";
|
||||
$message = "Aby zresetowac haslo przejdz pod adres:\n$url\n";
|
||||
$from = $GLOBALS['cfg']->applicationMail;
|
||||
$headers = "From: $from\r\nReply-To: $from";
|
||||
$ok = mail($email, $subject, $message, $headers);
|
||||
if ($ok)
|
||||
$msg = 'Na podany email wysłana została wiadomość z kluczem resetującym hasło.';
|
||||
else
|
||||
$msg = 'Niestety mailer nie działa, reset hasła jest chwilowo niemozliwy.';
|
||||
Daemon_MsgQueue::add($msg);
|
||||
return $ok;
|
||||
}
|
||||
|
||||
|
||||
//creates a new player
|
||||
public function register($login, $password, $passwordCopy)
|
||||
{
|
||||
$maxLength = $this->_dbClient->getColumnMaxLength('players', 'login');
|
||||
$validLogin = $this->validateLogin($login, $maxLength);
|
||||
$validPassword = $this->validatePassword($password, $passwordCopy);
|
||||
if($validLogin && $validPassword)
|
||||
{
|
||||
$salt = Daemon::passwordSalt();
|
||||
$passwordSql = sprintf('%s:%s', $salt, Daemon::passwordHash($salt, $password));
|
||||
$sql = "INSERT INTO players (login, password, roles) VALUES (:login, :password, 'chat')";
|
||||
$params = array('login' => $login, 'password' => $passwordSql);
|
||||
$ok = $this->_dbClient->query($sql, $params, 'Wybrany login jest już zajęty.');
|
||||
Daemon_MsgQueue::add(sprintf('Rejestracja zakończona %s.', $ok ? 'powodzeniem' : 'niepowodzeniem'));
|
||||
return $ok;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//resets password based on a hash key
|
||||
public function resetPassword($key)
|
||||
{
|
||||
$sql = "SELECT player_id FROM players WHERE reset_key = :key AND reset_until >= current_date";
|
||||
$params = array('key' => $key);
|
||||
$playerId = $this->_dbClient->selectValue($sql, $params);
|
||||
if ($playerId)
|
||||
{
|
||||
$sql = "UPDATE players SET password = reset_password, reset_password = null,
|
||||
reset_key = null, reset_until = null WHERE player_id = :id";
|
||||
$params = array('id' => $playerId);
|
||||
$ok = $this->_dbClient->query($sql, $params);
|
||||
Daemon_MsgQueue::add(sprintf('Zmiana hasła zakończona %s.', $ok ? 'powodzeniem' : 'niepowodzeniem'));
|
||||
}
|
||||
else
|
||||
Daemon_MsgQueue::add('Podany kod jest nieprawidłowy lub nieaktualny.');
|
||||
}
|
||||
|
||||
|
||||
//stores selected character's ID
|
||||
public function setCharacterId($id)
|
||||
{
|
||||
$_SESSION[self::VARNAME_CHARACTER_ID] = (int) $id;
|
||||
}
|
||||
|
||||
|
||||
//updates password
|
||||
public function setPassword($password, $passwordCopy)
|
||||
{
|
||||
if(!$password && !$passwordCopy)
|
||||
return;
|
||||
if($this->validatePassword($password, $passwordCopy))
|
||||
{
|
||||
$salt = Daemon::passwordSalt();
|
||||
$this->password = sprintf('%s:%s', $salt, Daemon::passwordHash($salt, $password));
|
||||
$this->put();
|
||||
Daemon_MsgQueue::add('Hasło zostało zmienione.');
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//deletes stored authentication data (logs out)
|
||||
public function unauthenticate()
|
||||
{
|
||||
unset($_SESSION[self::VARNAME_CHARACTER_ID]);
|
||||
unset($_SESSION[self::VARNAME_PLAYER_ID]);
|
||||
unset($_SESSION[self::VARNAME_PLAYER_ADDR]);
|
||||
unset($_SESSION[self::VARNAME_TIMESTAMP]);
|
||||
}
|
||||
|
||||
|
||||
//checks login validity
|
||||
private function validateLogin($input, $maxLength)
|
||||
{
|
||||
if(!$input)
|
||||
Daemon_MsgQueue::add('Musisz podać login.');
|
||||
elseif(iconv_strlen($input) > $maxLength)
|
||||
Daemon_MsgQueue::add('Wybrany login jest za długi.');
|
||||
else return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//checks gender validity
|
||||
private function validateGender($input)
|
||||
{
|
||||
if(!in_array($input, array_keys(Daemon_Dictionary::$genders)))
|
||||
Daemon_MsgQueue::add('Wybrana płeć nie jest dostępna.');
|
||||
else return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//checks name validity
|
||||
private function validateName($input, $maxLength)
|
||||
{
|
||||
if(!$input)
|
||||
Daemon_MsgQueue::add('Musisz podać imię.');
|
||||
elseif(iconv_strlen($input) > $maxLength)
|
||||
Daemon_MsgQueue::add('Wybrane imię jest za długie.');
|
||||
else return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//checks password validity
|
||||
private function validatePassword($input, $inputCopy)
|
||||
{
|
||||
if(!$input)
|
||||
Daemon_MsgQueue::add('Musisz podać hasło.');
|
||||
elseif($input != $inputCopy)
|
||||
Daemon_MsgQueue::add('Źle powtórzone hasło.');
|
||||
else return true;
|
||||
return false;
|
||||
}
|
||||
}
|
85
2013/daemon/lib/daemon/dictionary.php
Normal file
85
2013/daemon/lib/daemon/dictionary.php
Normal file
|
@ -0,0 +1,85 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Dictionary
|
||||
{
|
||||
public static $bossStatuses = array('hidden' => 'ukryty', 'active' => 'aktywny', 'defeated' => 'pokonany');
|
||||
|
||||
public static $characterAttributes = array(
|
||||
'str' => 'Siła', 'dex' => 'Zręczność', 'vit' => 'Wytrzymałość', 'pwr' => 'Moc', 'wil' => 'Siła Woli');
|
||||
|
||||
public static $characterSkills = array(
|
||||
'pstr' => 'Silny Cios', 'patk' => 'Przycelowanie',
|
||||
'pdef' => 'Unik', 'pres' => 'Twardziel', 'preg' => 'Regeneracja',
|
||||
'mstr' => 'Koncentracja', 'matk' => 'Magia Bojowa',
|
||||
'mdef' => 'Kontrzaklęcie', 'mres' => 'Antymagia', 'mreg' => 'Medytacja');
|
||||
|
||||
public static $combatAttackTypes = array('p' => 'fizyczny', 'm' => 'magiczny');
|
||||
|
||||
public static $combatAttackSpecials = array(
|
||||
Daemon_DbObject_CombatUnit::SP_POISON => 'trucizna',
|
||||
Daemon_DbObject_CombatUnit::SP_VAMPIRE => 'wampiryzm',
|
||||
Daemon_DbObject_CombatUnit::SP_ETHER => 'eteryczny',
|
||||
Daemon_DbObject_CombatUnit::SP_BLOODY => 'krwawy',
|
||||
Daemon_DbObject_CombatUnit::SP_STUN => 'ogłuszenie',
|
||||
Daemon_DbObject_CombatUnit::SP_FACTION => 'nienawiść',
|
||||
Daemon_DbObject_CombatUnit::SP_SWARM => 'stado',
|
||||
);
|
||||
|
||||
public static $combatArmorSpecials = array(
|
||||
Daemon_DbObject_CombatUnit::SP_DEMON => 'demon',
|
||||
Daemon_DbObject_CombatUnit::SP_ANTIPOISON => 'odporność na trucizny',
|
||||
Daemon_DbObject_CombatUnit::SP_ANTIVAMP => 'odporność na wampiryzm',
|
||||
Daemon_DbObject_CombatUnit::SP_SHOCK => 'porażenie',
|
||||
Daemon_DbObject_CombatUnit::SP_FACTION => 'fanatyzm',
|
||||
);
|
||||
|
||||
public static $equipmentButtons = array('use' => 'użyj', 'equip' => 'załóż', 'unequip' => 'zdejmij');
|
||||
|
||||
public static $equipmentFlags = array('bound' => 'przypisany', 'identified' => 'zidentyfikowany');
|
||||
|
||||
public static $equipmentGroups = array(
|
||||
'weapon1h' => 'BROŃ 1R i TARCZE', 'weapon2h' => 'BROŃ 2R',
|
||||
'armor' => 'PANCERZE', 'helmet' => 'HEŁMY', 'gloves' => 'RĘKAWICE',
|
||||
'boots' => 'BUTY', 'pendant' => 'NASZYJNIKI', 'accesory' => 'DODATKI',
|
||||
'item' => 'INNE PRZEDMIOTY');
|
||||
|
||||
public static $equipmentSlots = array(
|
||||
'hand_a' => 'główna ręka', 'hand_b' => 'druga ręka',
|
||||
'armor' => 'pancerz', 'helmet' => 'hełm', 'gloves' => 'rękawice', 'boots' => 'buty',
|
||||
'pendant' => 'naszyjnik', 'accesory_a' => 'dodatek A', 'accesory_b' => 'dodatek B');
|
||||
|
||||
public static $genders = array('f' => 'kobieta', 'm' => 'mężczyzna', 'n' => 'nieokreślona');
|
||||
|
||||
public static $generatorItemTypes = array(
|
||||
'weapon1h' => 'broń 1R', 'weapon2h' => 'broń 2R',
|
||||
'armor' => 'pancerz', 'helmet' => 'hełm', 'gloves' => 'rękawice',
|
||||
'boots' => 'buty', 'pendant' => 'naszyjnik', 'accesory' => 'dodatek');
|
||||
|
||||
public static $itemTypes = array(
|
||||
'weapon1h' => 'broń 1R', 'weapon2h' =>'broń 2R',
|
||||
'armor' => 'pancerz', 'helmet' => 'hełm', 'gloves' => 'rękawice',
|
||||
'boots' => 'buty', 'pendant' => 'naszyjnik', 'accesory' => 'dodatek',
|
||||
'item' => 'niezakładalny');
|
||||
|
||||
public static $itemDamageTypes = array('' => 'brak', 'p' => 'fizyczne', 'm' => 'magiczne');
|
||||
|
||||
public static $itemWeaponTypes = array('weapon1h' => 'jednoręczna', 'weapon2h' =>'dwuręczna');
|
||||
|
||||
public static $itemArmorTypes = array(
|
||||
'armor' => 'pancerz', 'helmet' => 'hełm', 'gloves' => 'rękawice',
|
||||
'boots' => 'buty', 'pendant' => 'naszyjnik', 'accesory' => 'dodatek');
|
||||
|
||||
public static $locationTypes = array('normal' => 'zwykła', 'arena'=>'arena', 'caern'=>'caern', 'boss' => 'boss');
|
||||
|
||||
public static $missionProgress = array(
|
||||
'active' => 'aktywna', 'completed' => 'ukończona', 'rewarded' => 'nagrodzona');
|
||||
|
||||
public static $monsterClasses = array(1 => 'słaby', 2 => 'średni', 3 => 'silny', 4 => 'epicki');
|
||||
|
||||
public static $monsterClassLevels = array(1 => 0, 2 => 20, 3 => 45, 4 => 70);
|
||||
|
||||
public static $serviceTypes = array(
|
||||
'bank'=>'bank', 'healer' => 'uzdrowiciel', 'shop' => 'sklep', 'temple'=>'świątynia');
|
||||
|
||||
public static $skinDirUrls = array('Ciemny' => 'static/dark', 'Jasny' => 'static/light');
|
||||
}
|
182
2013/daemon/lib/daemon/duel.php
Normal file
182
2013/daemon/lib/daemon/duel.php
Normal file
|
@ -0,0 +1,182 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Duel
|
||||
{
|
||||
private $dbClient = null;
|
||||
private $characterData = null;
|
||||
private $combatLog;
|
||||
const WINNER_ACTOR = 'a';
|
||||
const WINNER_TARGET = 'b';
|
||||
|
||||
|
||||
public function attachCharacterData(Daemon_DbObject_CharacterData $characterData)
|
||||
{
|
||||
$this->characterData = $characterData;
|
||||
}
|
||||
|
||||
|
||||
public function attachDbClient(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
public function getCombatLog()
|
||||
{
|
||||
return $this->combatLog;
|
||||
}
|
||||
|
||||
|
||||
//returns target character's object
|
||||
private function getTarget($targetId)
|
||||
{
|
||||
$params = array('character_id' => $targetId);
|
||||
$cdata = new Daemon_DbObject_CharacterData();
|
||||
$cdata->attachDbClient($this->dbClient);
|
||||
$cdata->get($params);
|
||||
$sql = "SELECT name FROM characters WHERE character_id=:character_id";
|
||||
$cdata->_characterName = $this->dbClient->selectValue($sql, $params);
|
||||
return $cdata;
|
||||
}
|
||||
|
||||
|
||||
public function execute(Daemon_View $view, $locationType, $targetId)
|
||||
{
|
||||
$levelMultiplier = 1.2; //magic number!
|
||||
$attacker = $this->characterData;
|
||||
$defender = $this->getTarget($targetId);
|
||||
$winner = null;
|
||||
$winnerName = null;
|
||||
$winnerXp = 0;
|
||||
$winnerLevel = null;
|
||||
$loserName = null;
|
||||
$loserLevel = 0;
|
||||
$sql = "SELECT MAX(rollover_id) FROM rollovers";
|
||||
$rolloverId = $this->dbClient->selectValue($sql);
|
||||
//check if combat is possibile
|
||||
if(!$attacker->canAttack((array) $defender, $rolloverId, true))
|
||||
return null;
|
||||
//check combat type
|
||||
$combatType = $attacker->getCombatType((array) $defender, $locationType);
|
||||
if(!$combatType)
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie możesz zaatakować tej postaci.');
|
||||
return false;
|
||||
}
|
||||
$arena = ('arena' == $combatType);
|
||||
//pre-calculate xp rewards (depends on health, which changes in combat)
|
||||
$factionBonus = ($attacker->faction_id && $defender->faction_id
|
||||
&& ($attacker->faction_id != $defender->faction_id));
|
||||
$attackerLevel = $attacker->getEffectiveLevel($factionBonus);
|
||||
$defenderLevel = $defender->getEffectiveLevel($factionBonus);
|
||||
//execute combat
|
||||
$winner = $this->runCombat($defender, $combatType);
|
||||
//update winner
|
||||
if(self::WINNER_ACTOR == $winner)
|
||||
{
|
||||
$winnerChar = $attacker;
|
||||
$loserChar = $defender;
|
||||
$winnerXp = Daemon_Math::round($levelMultiplier * $defenderLevel);
|
||||
}
|
||||
elseif(self::WINNER_TARGET == $winner)
|
||||
{
|
||||
$winnerChar = $defender;
|
||||
$loserChar = $attacker;
|
||||
$winnerXp = Daemon_Math::round($levelMultiplier * $attackerLevel);
|
||||
}
|
||||
else
|
||||
{
|
||||
$winnerChar = null;
|
||||
$loserChar = null;
|
||||
}
|
||||
if($winnerChar && $loserChar)
|
||||
{
|
||||
$winnerName = $winnerChar->_characterName;
|
||||
$loserName = $loserChar->_characterName;
|
||||
$winnerChar->xp_free += $winnerXp;
|
||||
$sql = "UPDATE character_statistics SET duel_wins=duel_wins+1 WHERE character_id=:id";
|
||||
$this->dbClient->query($sql, array('id' => $winnerChar->character_id));
|
||||
$sql = "UPDATE character_statistics SET duel_losses=duel_losses+1 WHERE character_id=:id";
|
||||
$this->dbClient->query($sql, array('id' => $loserChar->character_id));
|
||||
}
|
||||
//save characters
|
||||
$attacker->put();
|
||||
$defender->put();
|
||||
//log duel
|
||||
$sql = "INSERT INTO duels(rollover_id, attacker_id, defender_id, type, winner, combat_log)
|
||||
VALUES (:rolloverId, :attackerId, :defenderId, :type, :winner, :combatLog)";
|
||||
$params = array('rolloverId' => $rolloverId,
|
||||
'attackerId' => $attacker->character_id, 'defenderId' => $defender->character_id,
|
||||
'type' => $combatType, 'winner' => $winner, 'combatLog' => $this->combatLog);
|
||||
$this->dbClient->query($sql, $params);
|
||||
//generate report
|
||||
$view->arena = $arena;
|
||||
$view->combatLog = $this->combatLog;
|
||||
$view->attackerName = $attacker->_characterName;
|
||||
$view->defenderName = $defender->_characterName;
|
||||
$view->winner = $winner;
|
||||
$view->winnerName = $winnerName;
|
||||
$view->winnerXp = $winnerXp;
|
||||
$view->winnerLevel = $winnerLevel;
|
||||
$view->loserName = $loserName;
|
||||
ob_start();
|
||||
$view->display('duelcombat.xml');
|
||||
$this->combatLog = ob_get_clean();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//executes combat, returns winner flag
|
||||
private function runCombat(Daemon_DbObject_CharacterData $target, $combatType)
|
||||
{
|
||||
$combat = new Daemon_Combat();
|
||||
$logger = new Daemon_Combat_Log();
|
||||
$combat->attachLogger($logger);
|
||||
//prepare units
|
||||
$attackerUnit = $this->characterData->getCombatUnit(true);
|
||||
$defenderUnit = $target->getCombatUnit(true);
|
||||
if('arena' == $combatType)
|
||||
{
|
||||
$attackerUnit->health = $attackerUnit->health_max;
|
||||
$defenderUnit->health = $defenderUnit->health_max;
|
||||
}
|
||||
//execute combat
|
||||
$combat->addUnit('a', $attackerUnit, true);
|
||||
$combat->addUnit('b', $defenderUnit, false);
|
||||
$combat->execute();
|
||||
$this->combatLog = (string) $logger;
|
||||
//check deaths
|
||||
$deathA = ($attackerUnit->health < 1);
|
||||
$deathB = ($defenderUnit->health < 1);
|
||||
//update characters health, gold & equipment, return winner
|
||||
if('arena' != $combatType)
|
||||
{
|
||||
$attackerUnit->put();
|
||||
$this->characterData->health = floor($attackerUnit->health);
|
||||
$defenderUnit->put();
|
||||
$target->health = floor($defenderUnit->health);
|
||||
}
|
||||
if($deathA && $deathB)
|
||||
{
|
||||
if('arena' != $combatType)
|
||||
{
|
||||
$this->characterData->setDeath(true);
|
||||
$target->setDeath(true, null);
|
||||
}
|
||||
return null;//double KO
|
||||
}
|
||||
elseif($deathA && !$deathB)
|
||||
{
|
||||
if('arena' != $combatType)
|
||||
$this->characterData->setDeath(true);
|
||||
return self::WINNER_TARGET;
|
||||
}
|
||||
elseif(!$deathA && $deathB)
|
||||
{
|
||||
if('arena' != $combatType)
|
||||
$target->setDeath(true);
|
||||
return self::WINNER_ACTOR;
|
||||
}
|
||||
else return null;//draw
|
||||
}
|
||||
}
|
28
2013/daemon/lib/daemon/email.php
Normal file
28
2013/daemon/lib/daemon/email.php
Normal file
|
@ -0,0 +1,28 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//wrapper for mail() function
|
||||
class Daemon_Email
|
||||
{
|
||||
public $from;
|
||||
public $to;
|
||||
public $replyTo;
|
||||
public $subject;
|
||||
public $message;
|
||||
|
||||
|
||||
public function __construct()
|
||||
{
|
||||
$this->from = sprintf('no-reply@%s', getenv('SERVER_NAME'));
|
||||
}
|
||||
|
||||
|
||||
public function send()
|
||||
{
|
||||
$headers = implode("\r\n", array(
|
||||
sprintf('From: %s', $this->from),
|
||||
'Content-Type:text/plain;charset=UTF-8',
|
||||
));
|
||||
echo "mail($this->to, $this->subject, $this->message, $headers);";
|
||||
exit;
|
||||
}
|
||||
}
|
47
2013/daemon/lib/daemon/errorhandler.php
Normal file
47
2013/daemon/lib/daemon/errorhandler.php
Normal file
|
@ -0,0 +1,47 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_ErrorHandler
|
||||
{
|
||||
public static $logDir;
|
||||
|
||||
|
||||
public static function errorHandler($errno, $errstr, $errfile, $errline)
|
||||
{
|
||||
$data = "LEVEL: $errno\nMESSAGE: $errstr\nFILE: $errfile\nLINE: $errline";
|
||||
$path = sprintf('%s/error.%s.log', self::$logDir, date('Ymd.His'));
|
||||
self::logError($path, $data);
|
||||
}
|
||||
|
||||
|
||||
public static function exceptionHandler(Exception $ex)
|
||||
{
|
||||
$data = sprintf("MESSAGE: %s\nCODE: %s\nFILE: %s\nLINE: %s\nBACKTRACE:\n%s",
|
||||
$ex->getMessage(), $ex->getCode(), $ex->getFile(), $ex->getLine(), $ex->getTraceAsString());
|
||||
$path = sprintf('%s/exception.%s.log', self::$logDir, date('Ymd.His'));
|
||||
self::logError($path, $data);
|
||||
}
|
||||
|
||||
|
||||
public static function logError($path, $data)
|
||||
{
|
||||
$stored = @file_put_contents($path, $data);
|
||||
if(!headers_sent())
|
||||
header('Content-Type:text/html;charset=UTF-8');
|
||||
echo'<!DOCTYPE html><html><meta charset="UTF-8"><title>500 Internal Server Error</title>';
|
||||
echo'<h1>Wystąpił błąd</h1>';
|
||||
echo'<p>Kod gry zrobił <q>Aaarghhh!</q> i przestał działać. Albo zdechła baza danych. Albo cokolwiek.</p>';
|
||||
if($stored)
|
||||
{
|
||||
echo '<p>Na szczęście nie zawiodło automatyczne logowanie błędów,'
|
||||
.' więc nie musisz nic robić poza szturchnięciem admina że jego badziew znow nie działa ;)</p>';
|
||||
}
|
||||
else
|
||||
{
|
||||
echo '<p>Na dokładkę zawiodło też automatyczne logowanie błędów,'
|
||||
.' więc to do Ciebie należy ciężkie zadanie powiadomienia o nim admina.'
|
||||
.' Pamiętaj żeby podać wszystkie możliwe informacje o błędzie,'
|
||||
.' ułatwi to lub w ogóle umożliwi jego wytropienie.</p>';
|
||||
}
|
||||
exit;
|
||||
}
|
||||
}
|
50
2013/daemon/lib/daemon/event.php
Normal file
50
2013/daemon/lib/daemon/event.php
Normal file
|
@ -0,0 +1,50 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Event
|
||||
{
|
||||
private $characterData = null;
|
||||
private $eventLog;
|
||||
|
||||
|
||||
public function attachCharacterData(Daemon_DbObject_CharacterData $characterData)
|
||||
{
|
||||
$this->characterData = $characterData;
|
||||
}
|
||||
|
||||
|
||||
public function attachDbClient(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
public function getEventLog()
|
||||
{
|
||||
return $this->eventLog;
|
||||
}
|
||||
|
||||
|
||||
public function execute(Daemon_View $view, $eventId, $params)
|
||||
{
|
||||
//fetch event info
|
||||
$sql = "SELECT name, handle FROM events WHERE event_id=:id";
|
||||
$event = $this->dbClient->selectRow($sql, array('id' => $eventId));
|
||||
if(!$event)
|
||||
$event = array('name' => '???', 'handle' => null);
|
||||
//check if event is implemented
|
||||
$className = "Daemon_Event_$event[handle]";
|
||||
if(class_exists($className, true) && is_subclass_of($className, 'Daemon_EventInterface'))
|
||||
{
|
||||
//valid event, execute it (may update character)
|
||||
$handler = new $className($this->dbClient, $this->characterData, $view);
|
||||
$this->eventLog = $handler->execute($params);
|
||||
}
|
||||
else
|
||||
{
|
||||
//no event, update character
|
||||
Daemon_MsgQueue::add("Nieznane zdarzenie: $event[name]");
|
||||
$this->characterData->setLocationEvent(array());
|
||||
$this->characterData->put();
|
||||
}
|
||||
}
|
||||
}
|
14
2013/daemon/lib/daemon/event/deadend.php
Normal file
14
2013/daemon/lib/daemon/event/deadend.php
Normal file
|
@ -0,0 +1,14 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Event_Deadend extends Daemon_EventInterface
|
||||
{
|
||||
|
||||
|
||||
public function execute($params)
|
||||
{
|
||||
$this->clearEvent();
|
||||
ob_start();
|
||||
$this->view->display('event/deadend.xml');
|
||||
return ob_get_clean();
|
||||
}
|
||||
}
|
12
2013/daemon/lib/daemon/event/help.php
Normal file
12
2013/daemon/lib/daemon/event/help.php
Normal file
|
@ -0,0 +1,12 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Event_Help extends Daemon_EventInterface
|
||||
{
|
||||
|
||||
|
||||
public function execute($params)
|
||||
{
|
||||
$this->clearEvent();
|
||||
return '<b>Aaarghhh!</b>';
|
||||
}
|
||||
}
|
31
2013/daemon/lib/daemon/event/intro.php
Normal file
31
2013/daemon/lib/daemon/event/intro.php
Normal file
|
@ -0,0 +1,31 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Event_Intro extends Daemon_EventInterface
|
||||
{
|
||||
|
||||
|
||||
public function execute($params)
|
||||
{
|
||||
$this->clearEvent();
|
||||
//check title
|
||||
$sql = "SELECT 1 FROM character_titles WHERE character_id=:id AND title_id='cultist'";
|
||||
$hasTitle = (bool) $this->dbClient->selectValue($sql, array('id' => $this->characterData->character_id));
|
||||
if(!$hasTitle)
|
||||
{
|
||||
//run combat
|
||||
$combat = new Daemon_MonsterCombat();
|
||||
$combat->attachCharacterData($this->characterData);
|
||||
$combat->attachDbClient($this->dbClient);
|
||||
$combat->execute($this->view, 'cultist', true);
|
||||
$combatLog = $combat->getCombatLog();
|
||||
unset($combat);
|
||||
}
|
||||
else $combatLog = null;
|
||||
//display log
|
||||
ob_start();
|
||||
$this->view->combatLog = $combatLog;
|
||||
$this->view->hasTitle = $hasTitle;
|
||||
$this->view->display('event/intro.xml');
|
||||
return ob_get_clean();
|
||||
}
|
||||
}
|
27
2013/daemon/lib/daemon/eventinterface.php
Normal file
27
2013/daemon/lib/daemon/eventinterface.php
Normal file
|
@ -0,0 +1,27 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
abstract class Daemon_EventInterface
|
||||
{
|
||||
protected $characterData;
|
||||
protected $dbClient;
|
||||
protected $view;
|
||||
|
||||
|
||||
final public function __construct(Daemon_DbClient $dbClient,
|
||||
Daemon_DbObject_CharacterData $characterData, Daemon_View $view)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
$this->characterData = $characterData;
|
||||
$this->view = $view;
|
||||
}
|
||||
|
||||
|
||||
final protected function clearEvent()
|
||||
{
|
||||
$this->characterData->setLocationEvent(array());
|
||||
$this->characterData->put();
|
||||
}
|
||||
|
||||
|
||||
abstract public function execute($params);
|
||||
}
|
119
2013/daemon/lib/daemon/forum.php
Normal file
119
2013/daemon/lib/daemon/forum.php
Normal file
|
@ -0,0 +1,119 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//mail & chat related operations
|
||||
class Daemon_Forum
|
||||
{
|
||||
private $dbClient;
|
||||
|
||||
|
||||
public function __construct(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
//adds new mail message
|
||||
public function addChat($senderId, $channelId, $content)
|
||||
{
|
||||
$content = Daemon::normalizeString($content, true);
|
||||
if($content)
|
||||
{
|
||||
$sql = "INSERT INTO chat (sender_id, channel_id, content) VALUES (:senderId, :channelId, :content)";
|
||||
$params = array('senderId' => $senderId, 'channelId' => $channelId, 'content' => $content);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
else Daemon_MsgQueue::add('Podaj treść wiadomości.');
|
||||
}
|
||||
|
||||
|
||||
//adds new mail message
|
||||
public function addMail($senderId, $recipientName, $content)
|
||||
{
|
||||
if($recipientId = $this->getCharacterIdByName($recipientName))
|
||||
$this->addMailById($senderId, $recipientId, $content);
|
||||
else Daemon_MsgQueue::add('Wybrany adresat nie istnieje.');
|
||||
}
|
||||
|
||||
|
||||
//adds new mail message
|
||||
public function addMailById($senderId, $recipientId, $content)
|
||||
{
|
||||
$content = Daemon::normalizeString($content, true);
|
||||
if($content)
|
||||
{
|
||||
$sql = "INSERT INTO mail (sender_id, recipient_id, content) VALUES (:senderId, :recipientId, :content)";
|
||||
$params = array('senderId' => $senderId, 'recipientId' => $recipientId, 'content' => $content);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
else Daemon_MsgQueue::add('Podaj treść wiadomości.');
|
||||
}
|
||||
|
||||
|
||||
//updates message with "reply" link
|
||||
private static function callbackReplyLink(&$row, $key, $characterId)
|
||||
{
|
||||
if($row['sender_id'] && ($row['sender_id'] != $characterId))
|
||||
$row['replyUrl'] = sprintf('?to=%s', urlencode($row['sender_name']));
|
||||
}
|
||||
|
||||
|
||||
//finds character Id by its name
|
||||
private function getCharacterIdByName($name)
|
||||
{
|
||||
$sql = "SELECT character_id FROM characters WHERE name = :name";
|
||||
return $this->dbClient->selectValue($sql, array('name' => Daemon::normalizeString($name)));
|
||||
}
|
||||
|
||||
|
||||
//fetches messages from selected channel
|
||||
public function getChat($limit, $from, $channelId)
|
||||
{
|
||||
$params = array('limit' => $limit + 1, 'channelId' => $channelId);
|
||||
$cond = 'channel_id = :channelId';
|
||||
if($from)
|
||||
{
|
||||
$cond .= ' AND message_id <= :from';
|
||||
$params['from'] = (int) $from;
|
||||
}
|
||||
$sql = "SELECT m.*, s.name AS sender_name
|
||||
FROM chat m LEFT JOIN characters s ON s.character_id = m.sender_id
|
||||
WHERE $cond ORDER BY message_id DESC LIMIT :limit";
|
||||
$list = $this->dbClient->selectAll($sql, $params);
|
||||
if(count($list) > $limit)
|
||||
{
|
||||
$next = array_pop($list);
|
||||
$next = $next['message_id'];
|
||||
}
|
||||
else $next = null;
|
||||
return array('list' => $list, 'next' => $next);
|
||||
}
|
||||
|
||||
|
||||
//fetches character's mailbox
|
||||
public function getMail($limit, $from, $characterId)
|
||||
{
|
||||
$params = array('limit' => $limit + 1, 'cid1' => $characterId, 'cid2' => $characterId);
|
||||
$cond = '(sender_id = :cid1 OR recipient_id = :cid2)';
|
||||
if($from)
|
||||
{
|
||||
$cond .= ' AND message_id <= :from';
|
||||
$params['from'] = (int) $from;
|
||||
}
|
||||
$sql = "SELECT m.*, s.name AS sender_name, r.name AS recipient_name
|
||||
FROM mail m
|
||||
LEFT JOIN characters s ON s.character_id = m.sender_id
|
||||
LEFT JOIN characters r ON r.character_id = m.recipient_id
|
||||
WHERE $cond ORDER BY message_id DESC LIMIT :limit";
|
||||
|
||||
$list = $this->dbClient->selectAll($sql, $params);
|
||||
if(count($list) > $limit)
|
||||
{
|
||||
$next = array_pop($list);
|
||||
$next = $next['message_id'];
|
||||
}
|
||||
else $next = null;
|
||||
if($list)
|
||||
array_walk($list, array(get_class($this), 'callbackReplyLink'), $characterId);
|
||||
return array('list' => $list, 'next' => $next);
|
||||
}
|
||||
}
|
154
2013/daemon/lib/daemon/inventory.php
Normal file
154
2013/daemon/lib/daemon/inventory.php
Normal file
|
@ -0,0 +1,154 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Inventory
|
||||
{
|
||||
private $dbClient = null;
|
||||
private $characterData = null;
|
||||
|
||||
|
||||
public function __construct(Daemon_DbClient $dbClient, Daemon_DbObject_CharacterData $characterData)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
$this->characterData = $characterData;
|
||||
}
|
||||
|
||||
|
||||
//equips selected item
|
||||
public function equip($inventoryId, $slot)
|
||||
{
|
||||
//check item
|
||||
$sql = "SELECT item_id FROM inventory WHERE inventory_id=:id AND character_id=:charId";
|
||||
$params = array('id' => $inventoryId, 'charId' => $this->characterData->character_id);
|
||||
$id = $this->dbClient->selectValue($sql, $params);
|
||||
$item = new Daemon_DbObject_Item();
|
||||
$item->attachDbClient($this->dbClient);
|
||||
$item->get(array('item_id' => $id));
|
||||
$slots = $item->getSlots();
|
||||
//check slot
|
||||
if(!in_array($slot, $slots))
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie możesz załozyć tego przedmiotu.');
|
||||
return false;
|
||||
}
|
||||
//check for 2h weapon equipped
|
||||
$sql = "SELECT 'weapon2h'=i.type FROM inventory inv JOIN items i USING(item_id)
|
||||
WHERE character_id=:charId AND equipped='hand_a'";
|
||||
$params = array('charId' => $this->characterData->character_id);
|
||||
$zweihander = (bool) $this->dbClient->selectValue($sql, $params);
|
||||
//equip item, unequip previous item(s)
|
||||
if( ('weapon2h' == $item->type) || (('weapon1h' == $item->type) && $zweihander) )//2h equipping or equipped
|
||||
$unequipSlots = "'hand_a','hand_b'";
|
||||
else $unequipSlots = "'$slot'";
|
||||
$sql = "UPDATE inventory SET equipped = IF(inventory_id=:id, :slot, null)
|
||||
WHERE character_id=:charId AND (inventory_id=:id OR equipped IN ($unequipSlots))";
|
||||
$params = array('id' => $inventoryId, 'charId' => $this->characterData->character_id, 'slot' => $slot);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//creates equipment array based on items list
|
||||
public function getEquipment(array $items)
|
||||
{
|
||||
$result = array();
|
||||
foreach(Daemon_Dictionary::$equipmentSlots as $slot => $name)
|
||||
$result[$slot] = array('slotName' => $name, 'inventoryId' => null, 'flags' => null, 'item' => null);
|
||||
foreach($items as $row)
|
||||
{
|
||||
if(isset($result[$row['equipped']]))
|
||||
{
|
||||
$result[$row['equipped']]['inventoryId'] = $row['inventory_id'];
|
||||
$result[$row['equipped']]['flags'] = $row['flags'];
|
||||
$result[$row['equipped']]['item'] = $row['item'];
|
||||
}
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
//fetches a detailed list of character's items
|
||||
public function getItems($status, $withoutEquipment = false)
|
||||
{
|
||||
$cond = "inv.character_id=:characterId";
|
||||
if($status)
|
||||
$cond .= " AND inv.status=:status";
|
||||
if($withoutEquipment)
|
||||
$cond .= " AND equipped IS NULL";
|
||||
$sql = "SELECT inv.inventory_id, inv.item_id, inv.status, inv.flags, inv.equipped
|
||||
FROM inventory inv JOIN items i USING(item_id)
|
||||
WHERE $cond ORDER BY i.type, i.name, inv.inventory_id";
|
||||
$params = array('characterId' => $this->characterData->character_id);
|
||||
if($status)
|
||||
$params['status'] = $status;
|
||||
if($data = $this->dbClient->selectAll($sql, $params))
|
||||
{
|
||||
$result = array();
|
||||
foreach($data as $row)
|
||||
{
|
||||
$row['_equipped'] = false;
|
||||
if($row['flags'])
|
||||
$row['flags'] = array_fill_keys(explode(',', $row['flags']), true);
|
||||
else $row['flags'] = array();
|
||||
$row['item'] = new Daemon_DbObject_Item();
|
||||
$row['item']->attachDbClient($this->dbClient);
|
||||
$row['item']->get(array('item_id' => $row['item_id']));
|
||||
$result[$row['inventory_id']] = $row;
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
else return array();
|
||||
}
|
||||
|
||||
|
||||
//groups items by status (equipped/inventory/storage)
|
||||
public function groupItemsByStatus(array $items)
|
||||
{
|
||||
$result = array();
|
||||
foreach($items as $id => $row)
|
||||
{
|
||||
$status = $row['status'];
|
||||
if(('inventory' == $status) && $row['equipped'])
|
||||
$status = 'equipment';
|
||||
$result[$status]['items'][$id] = $row;
|
||||
}
|
||||
$groupNames = array('equipment' => 'Ekwipunek', 'inventory' => 'Plecak', 'storage' => 'Schowek');
|
||||
foreach(array_keys($result) as $key)
|
||||
{
|
||||
if(isset($groupNames[$key]))
|
||||
$result[$key]['name'] = $groupNames[$key];
|
||||
else unset($groupNames[$key]);
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
//groups items by type
|
||||
public function groupItemsByType(array $items)
|
||||
{
|
||||
$result = array();
|
||||
$groupNames = Daemon_Dictionary::$equipmentGroups;
|
||||
foreach ($groupNames as $key => $name)
|
||||
$result[$key] = array('name' => $name, 'items' => array());
|
||||
foreach($items as $id => $row)
|
||||
{
|
||||
$type = $row['item']->type;
|
||||
$result[$type]['items'][$id] = $row;
|
||||
}
|
||||
foreach(array_keys($result) as $key)
|
||||
{
|
||||
if (empty($result[$key]['items']))
|
||||
unset($result[$key]);
|
||||
elseif (empty($result[$key]['name']))
|
||||
$result[$key]['name'] = '???';
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
//unequips selected item
|
||||
public function unequip($inventoryId)
|
||||
{
|
||||
$sql = "UPDATE inventory SET equipped=null WHERE inventory_id=:id AND character_id=:charId";
|
||||
$params = array('id' => $inventoryId, 'charId' => $this->characterData->character_id);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
}
|
54
2013/daemon/lib/daemon/item.php
Normal file
54
2013/daemon/lib/daemon/item.php
Normal file
|
@ -0,0 +1,54 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Item
|
||||
{
|
||||
private $characterData = null;
|
||||
private $usageLog;
|
||||
|
||||
|
||||
public function attachCharacterData(Daemon_DbObject_CharacterData $characterData)
|
||||
{
|
||||
$this->characterData = $characterData;
|
||||
}
|
||||
|
||||
|
||||
public function attachDbClient(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
public function getUsageLog()
|
||||
{
|
||||
return $this->usageLog;
|
||||
}
|
||||
|
||||
|
||||
public function execute(Daemon_View $view, $inventoryId)
|
||||
{
|
||||
//fetch item data
|
||||
$sql = "SELECT s.handle, i.special_param AS params
|
||||
FROM inventory inv JOIN items i USING(item_id)
|
||||
LEFT JOIN item_specials s ON s.special_id = i.special_type
|
||||
WHERE inv.character_id=:charId AND inv.inventory_id=:id AND i.type='item'";
|
||||
$params = array('charId' => $this->characterData->character_id, 'id' => $inventoryId);
|
||||
$item = $this->dbClient->selectRow($sql, $params);
|
||||
if(!$item)
|
||||
$item = array('handle' => null, 'params' => null);
|
||||
//check if handler is implemented
|
||||
$className = "Daemon_Item_$item[handle]";
|
||||
if(class_exists($className, true) && is_subclass_of($className, 'Daemon_ItemInterface'))
|
||||
{
|
||||
//valid event, execute it (may update character)
|
||||
$handler = new $className($this->dbClient, $this->characterData, $view);
|
||||
$this->usageLog = $handler->execute($inventoryId, $item['params']);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
//no effect
|
||||
Daemon_MsgQueue::add('Nie masz pojęcia do czego to może służyć.');
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
33
2013/daemon/lib/daemon/item/givespell.php
Normal file
33
2013/daemon/lib/daemon/item/givespell.php
Normal file
|
@ -0,0 +1,33 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Item_GiveSpell extends Daemon_ItemInterface
|
||||
{
|
||||
|
||||
|
||||
public function execute($inventoryId, $spellId)
|
||||
{
|
||||
$char = $this->characterData;
|
||||
//get spell data
|
||||
$sql = "SELECT * FROM spells WHERE spell_id=:id";
|
||||
$spell = $this->dbClient->selectRow($sql, array('id' => $spellId));
|
||||
if(!$spell)
|
||||
return 'Takie zaklęcie nie istnieje.';
|
||||
//give spell to character
|
||||
$colName = "sp_$spellId";
|
||||
if(($char->$colName > 0) && ($char->$colName <= $spell['min_cost']))
|
||||
return "Zaklęcie $spell[name] znasz już na poziomie mistrzowskim.";
|
||||
if($char->$colName < 1)
|
||||
{
|
||||
$msg = "Poznajesz nowe zaklęcie: $spell[name].";
|
||||
$char->$colName = $spell['max_cost'];
|
||||
}
|
||||
elseif($char->$colName > $spell['min_cost'])
|
||||
{
|
||||
$msg = "Lepiej poznajesz zaklęcie $spell[name] - potrzebujesz mniej many by je rzucić.";
|
||||
$char->$colName -= round(($spell['max_cost'] - $spell['min_cost']) / ($spell['max_level'] - 1));
|
||||
}
|
||||
$char->put();
|
||||
$this->deleteItem($inventoryId);
|
||||
return $msg;
|
||||
}
|
||||
}
|
32
2013/daemon/lib/daemon/item/heal.php
Normal file
32
2013/daemon/lib/daemon/item/heal.php
Normal file
|
@ -0,0 +1,32 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Item_Heal extends Daemon_ItemInterface
|
||||
{
|
||||
|
||||
|
||||
public function execute($inventoryId, $params)
|
||||
{
|
||||
$msg = '';
|
||||
$char = $this->characterData;
|
||||
$params = explode(',', $params);
|
||||
$deltaHealth = isset($params[0]) ? (int) $params[0] : 0;
|
||||
$deltaMana = isset($params[1]) ? (int) $params[1] : 0;
|
||||
if($deltaHealth)
|
||||
{
|
||||
$oldValue = $char->health;
|
||||
$char->health = min($char->health_max, $char->health + $deltaHealth);
|
||||
$deltaHealth = $char->health - $oldValue;
|
||||
$msg[] = "zdrowie: +$deltaHealth";
|
||||
}
|
||||
if($deltaMana)
|
||||
{
|
||||
$oldValue = $char->mana;
|
||||
$char->mana = min($char->mana_max, $char->mana + $deltaMana);
|
||||
$deltaMana = $char->mana - $oldValue;
|
||||
$msg[] = "mana: +$deltaMana";
|
||||
}
|
||||
$char->put();
|
||||
$this->deleteItem($inventoryId);
|
||||
return implode(', ', $msg);
|
||||
}
|
||||
}
|
15
2013/daemon/lib/daemon/item/teleport.php
Normal file
15
2013/daemon/lib/daemon/item/teleport.php
Normal file
|
@ -0,0 +1,15 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Item_Teleport extends Daemon_ItemInterface
|
||||
{
|
||||
|
||||
|
||||
public function execute($inventoryId, $locationId)
|
||||
{
|
||||
$this->characterData->location_id = $locationId;
|
||||
$this->characterData->put();
|
||||
$this->deleteItem($inventoryId);
|
||||
return "Nagle znajdujesz się zupełnie gdzieindziej...";
|
||||
}
|
||||
}
|
||||
|
28
2013/daemon/lib/daemon/iteminterface.php
Normal file
28
2013/daemon/lib/daemon/iteminterface.php
Normal file
|
@ -0,0 +1,28 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
abstract class Daemon_ItemInterface
|
||||
{
|
||||
protected $characterData;
|
||||
protected $dbClient;
|
||||
protected $view;
|
||||
|
||||
|
||||
final public function __construct(Daemon_DbClient $dbClient,
|
||||
Daemon_DbObject_CharacterData $characterData, Daemon_View $view)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
$this->characterData = $characterData;
|
||||
$this->view = $view;
|
||||
}
|
||||
|
||||
|
||||
final protected function deleteItem($inventoryId)
|
||||
{
|
||||
$sql = "DELETE FROM inventory WHERE character_id=:charId AND inventory_id=:id";
|
||||
$params = array('charId' => $this->characterData->character_id, 'id' => $inventoryId);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
abstract public function execute($inventoryId, $params);
|
||||
}
|
57
2013/daemon/lib/daemon/math.php
Normal file
57
2013/daemon/lib/daemon/math.php
Normal file
|
@ -0,0 +1,57 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Math
|
||||
{
|
||||
//calculates regen value from skill and armor bonus
|
||||
public static function combatRegen($attribute, $skill)
|
||||
{
|
||||
if($sum = $attribute + $skill)
|
||||
return round($attribute * $skill / $sum, 3);
|
||||
else return 0.0;
|
||||
}
|
||||
|
||||
|
||||
//calculates a single stat
|
||||
public static function combatStat($attribute, $bonus_p, $bonus_c, $skill)
|
||||
{
|
||||
return max(0, (int) round($attribute * (1 + $bonus_p/100) + $bonus_c + $skill));
|
||||
}
|
||||
|
||||
|
||||
//calculates power multiplier for faction boss
|
||||
public static function factionPowerMult($bossFactionId, array $factionPowers)
|
||||
{
|
||||
$sum = array_sum($factionPowers);
|
||||
if(empty($sum) || !isset($factionPowers[$bossFactionId]))
|
||||
return 1;
|
||||
return 1 + $factionPowers[$bossFactionId] / $sum;
|
||||
}
|
||||
|
||||
|
||||
//calculates mana regen value from skill
|
||||
public static function manaRegen($attribute, $skill)
|
||||
{
|
||||
if($sum = $attribute + $skill)
|
||||
return max(1, (int) round($attribute * $skill / $sum));
|
||||
else return 1;
|
||||
}
|
||||
|
||||
|
||||
//calculates spell cost
|
||||
public static function spellCost($level, $maxCost, $minCost, $delta)
|
||||
{
|
||||
$level = max(1, $level);
|
||||
return max($minCost, $maxCost - $level * $delta);
|
||||
}
|
||||
|
||||
|
||||
//randomly rounds a number
|
||||
public static function round($float)
|
||||
{
|
||||
$result = floor($float);
|
||||
$prob = $float - $result;
|
||||
if(mt_rand(0,255) < 256 * $prob)
|
||||
++$result;
|
||||
return (int) $result;
|
||||
}
|
||||
}
|
183
2013/daemon/lib/daemon/monstercombat.php
Normal file
183
2013/daemon/lib/daemon/monstercombat.php
Normal file
|
@ -0,0 +1,183 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_MonsterCombat
|
||||
{
|
||||
private $dbClient = null;
|
||||
private $characterData = null;
|
||||
private $combatLog;
|
||||
const WINNER_ACTOR = 'a';
|
||||
const WINNER_MONSTER = 'm';
|
||||
|
||||
|
||||
public function attachCharacterData(Daemon_DbObject_CharacterData $characterData)
|
||||
{
|
||||
$this->characterData = $characterData;
|
||||
}
|
||||
|
||||
|
||||
public function attachDbClient(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
public function getCombatLog()
|
||||
{
|
||||
return $this->combatLog;
|
||||
}
|
||||
|
||||
|
||||
public function execute(Daemon_View $view, $monsterId, $fromEvent = false)
|
||||
{
|
||||
$char = $this->characterData;
|
||||
$winner = null;
|
||||
$winnerXp = 0;
|
||||
$winnerGold = null;
|
||||
$winnerLevel = null;
|
||||
$winnerDrop = null;
|
||||
$winnerMission = null;
|
||||
//load monster
|
||||
$monster = new Daemon_DbObject_Monster();
|
||||
$monster->attachDbClient($this->dbClient);
|
||||
$monster->get(array('monster_id' => $monsterId));
|
||||
//execute combat
|
||||
$winner = $this->runCombat($monster);
|
||||
//check for winner, modify character
|
||||
if(self::WINNER_ACTOR == $winner)
|
||||
{
|
||||
//experience
|
||||
$winnerXp = $monster->level;
|
||||
$this->characterData->xp_free += $winnerXp;
|
||||
//gold
|
||||
$winnerGold = $monster->gold;
|
||||
$this->characterData->gold_purse += $winnerGold;
|
||||
//level
|
||||
if($monster->level > $this->characterData->level)
|
||||
{
|
||||
$winnerLevel = $monster->level;
|
||||
$this->characterData->level = $winnerLevel;
|
||||
}
|
||||
else $winnerLevel = null;
|
||||
//statistics
|
||||
if(($monster->class >=1) && ($monster->class<=4))
|
||||
{
|
||||
$colname = "kills_mob{$monster->class}";
|
||||
$sql = "UPDATE character_statistics SET $colname=$colname+1 WHERE character_id=:id";
|
||||
$this->dbClient->query($sql, array('id' => $this->characterData->character_id));
|
||||
}
|
||||
//drop
|
||||
$winnerDrop = $this->rollDrop($monster);
|
||||
//title
|
||||
if($monster->title_id)
|
||||
{
|
||||
$sql = "INSERT IGNORE INTO character_titles(character_id, title_id) VALUES(:charId, :titleId)";
|
||||
$params = array(
|
||||
'charId' => $this->characterData->character_id,
|
||||
'titleId' => $monster->title_id);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
//mission
|
||||
$mission = $this->characterData->getLastMission('active');
|
||||
if(('monster' == $mission['type']) && ($monster->monster_id == $mission['params']))
|
||||
{
|
||||
$sql = "UPDATE character_missions SET progress='completed'
|
||||
WHERE character_id=:cid AND rollover_id=:rid";
|
||||
$params = array('cid' => $this->characterData->character_id, 'rid' => $mission['rollover_id']);
|
||||
$this->dbClient->query($sql, $params);
|
||||
$winnerMission = true;
|
||||
}
|
||||
}
|
||||
elseif(self::WINNER_MONSTER == $winner)
|
||||
$this->characterData->setDeath(true);
|
||||
//update character
|
||||
$this->characterData->setLocationEvent(array());
|
||||
$this->characterData->put();
|
||||
//generate report
|
||||
$view->combatLog = $this->combatLog;
|
||||
$view->fromEvent = $fromEvent;
|
||||
$view->monsterName = $monster->name;
|
||||
$view->winner = $winner;
|
||||
$view->winnerXp = $winnerXp;
|
||||
$view->winnerGold = $winnerGold;
|
||||
$view->winnerLevel = $winnerLevel;
|
||||
$view->winnerDrop = $winnerDrop;
|
||||
$view->winnerMission = $winnerMission;
|
||||
ob_start();
|
||||
$view->display('monstercombat.xml');
|
||||
$this->combatLog = ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
//rolls for monster drops, return array of item names
|
||||
private function rollDrop(Daemon_DbObject_Monster $monster)
|
||||
{
|
||||
$itemId = null;
|
||||
$itemName = null;
|
||||
//check if there was any drop
|
||||
if($monster->chance2)
|
||||
{
|
||||
$d256 = mt_rand(0, 255);
|
||||
$chance = 256 * $monster->chance1 / $monster->chance2;
|
||||
$itemId = ($d256 < $chance);
|
||||
}
|
||||
if($itemId)
|
||||
{
|
||||
$itemId = null;
|
||||
//read drops
|
||||
$sql = "SELECT item_id, chance, name FROM monster_drops JOIN items USING(item_id) WHERE monster_id=:id";
|
||||
$drops = $this->dbClient->selectAll($sql, array('id' => $monster->monster_id));
|
||||
//roll drop
|
||||
$chanceSum = 0;
|
||||
foreach($drops as $row)
|
||||
$chanceSum += $row['chance'];
|
||||
$d256 = mt_rand(0, 255);
|
||||
foreach($drops as $row)
|
||||
{
|
||||
$chance = 256 * $row['chance'] / $chanceSum;
|
||||
if($d256 < $chance)
|
||||
{
|
||||
$itemId = $row['item_id'];
|
||||
$itemName = $row['name'];
|
||||
break;
|
||||
}
|
||||
$d256 -= $chance;
|
||||
}
|
||||
//give drop
|
||||
if($itemId)
|
||||
{
|
||||
$sql = "INSERT INTO inventory(character_id, item_id) VALUES (:charId, :itemId)";
|
||||
$params = array('charId' => $this->characterData->character_id, 'itemId' => $itemId);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
}
|
||||
return $itemName;
|
||||
}
|
||||
|
||||
|
||||
//executes combat, returns winner flag
|
||||
private function runCombat(Daemon_DbObject_Monster $monster)
|
||||
{
|
||||
$combat = new Daemon_Combat();
|
||||
$logger = new Daemon_Combat_Log();
|
||||
$combat->attachLogger($logger);
|
||||
//prepare units
|
||||
$characterUnit = $this->characterData->getCombatUnit(true);
|
||||
$monsterUnit = $monster->getCombatUnit(true);
|
||||
$monsterUnit->health = $monsterUnit->health_max;
|
||||
//add units
|
||||
$combat->addUnit('a', $characterUnit, true);
|
||||
$combat->addUnit('b', $monsterUnit, false);
|
||||
//execute combat
|
||||
$combat->execute();
|
||||
$this->combatLog = (string) $logger;
|
||||
//update character
|
||||
$characterUnit->put();
|
||||
$this->characterData->health = floor($characterUnit->health);
|
||||
//check winner
|
||||
if($this->characterData->health < 1)
|
||||
return self::WINNER_MONSTER;
|
||||
if($monsterUnit->health < 1)
|
||||
return self::WINNER_ACTOR;
|
||||
return null;
|
||||
}
|
||||
}
|
27
2013/daemon/lib/daemon/msgqueue.php
Normal file
27
2013/daemon/lib/daemon/msgqueue.php
Normal file
|
@ -0,0 +1,27 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
// session-based message queue
|
||||
class Daemon_MsgQueue
|
||||
{
|
||||
const VARNAME = 'msg';
|
||||
|
||||
|
||||
public static function add($txt)
|
||||
{
|
||||
$_SESSION[self::VARNAME][] = (string)$txt;
|
||||
}
|
||||
|
||||
|
||||
public static function getAll()
|
||||
{
|
||||
if(isset($_SESSION[self::VARNAME]))
|
||||
{
|
||||
$messages = (array) $_SESSION[self::VARNAME];
|
||||
unset($_SESSION[self::VARNAME]);
|
||||
return $messages;
|
||||
}
|
||||
else return null;
|
||||
}
|
||||
|
||||
|
||||
}
|
72
2013/daemon/lib/daemon/news.php
Normal file
72
2013/daemon/lib/daemon/news.php
Normal file
|
@ -0,0 +1,72 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_News
|
||||
{
|
||||
private $dbClient;
|
||||
|
||||
|
||||
public function __construct(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
protected function callbackFormatDates(&$row)
|
||||
{
|
||||
$row['published'] = date(DATE_ATOM, $row['published_ts']);
|
||||
$row['updated'] = date(DATE_ATOM, $row['updated_ts']);
|
||||
}
|
||||
|
||||
|
||||
//deletes entry by ID
|
||||
public function deleteEntry($id)
|
||||
{
|
||||
$sql = "DELETE FROM newsfeed WHERE id=:id";
|
||||
$this->dbClient->query($sql, array('id' => $id));
|
||||
}
|
||||
|
||||
|
||||
//generates an ID for a new entry
|
||||
public function generateId($domain, $title)
|
||||
{
|
||||
$suffix = preg_replace('/\W+/', '-', $title);
|
||||
return sprintf('tag:%s,%s:%s', $domain, date('Y-m-d'), $suffix);
|
||||
}
|
||||
|
||||
|
||||
//fetches last entry's update time
|
||||
public function getLastUpdated()
|
||||
{
|
||||
$sql = "SELECT UNIX_TIMESTAMP(MAX(updated)) FROM newsfeed";
|
||||
return date(DATE_ATOM, (int) $this->dbClient->selectValue($sql, array()));
|
||||
}
|
||||
|
||||
|
||||
//fetches a list of last entries
|
||||
public function getEntries($limit, $format = false)
|
||||
{
|
||||
$params = array();
|
||||
$sql = "SELECT *, UNIX_TIMESTAMP(published) AS published_ts, UNIX_TIMESTAMP(updated) AS updated_ts
|
||||
FROM newsfeed ORDER BY published DESC";
|
||||
if($limit)
|
||||
{
|
||||
$params = array('limit' => $limit);
|
||||
$sql .= " LIMIT :limit";
|
||||
}
|
||||
$data = $this->dbClient->selectAll($sql, $params);
|
||||
if($format && $data)
|
||||
array_walk($data, array($this, 'callbackFormatDates'));
|
||||
return $data;
|
||||
}
|
||||
|
||||
|
||||
//creates or updates a feed entry
|
||||
public function updateEntry($id, $title, $author, $content)
|
||||
{
|
||||
$sql = "INSERT INTO newsfeed (id, published, title, author, content)
|
||||
VALUES (:id, NOW(), :title, :author, :content)
|
||||
ON DUPLICATE KEY UPDATE updated=NOW(), title=:title, author=:author, content=:content";
|
||||
$params = array('id' => $id, 'title' => $title, 'author' => $author, 'content' => $content);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
}
|
73
2013/daemon/lib/daemon/scyzoryk.php
Normal file
73
2013/daemon/lib/daemon/scyzoryk.php
Normal file
|
@ -0,0 +1,73 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
require'daemon/scyzoryk/dbrow.php';
|
||||
class Daemon_Scyzoryk
|
||||
{
|
||||
protected $dbClient;
|
||||
|
||||
|
||||
public function __construct(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
public function deleteRows($tableName, $indexCol, array $ids)
|
||||
{
|
||||
$sql = "DELETE FROM $tableName WHERE $indexCol=:id";
|
||||
foreach($ids as $id)
|
||||
$this->dbClient->query($sql, array('id' => $id));
|
||||
}
|
||||
|
||||
|
||||
public function selectRow($className, $id, $id2 = null)
|
||||
{
|
||||
$tableName = constant("$className::TABLE_NAME");
|
||||
$indexCol = constant("$className::INDEX_COL");
|
||||
$indexCol2 = constant("$className::INDEX_COL2");
|
||||
if(!$tableName || !$indexCol)
|
||||
throw new InvalidArgumentException('Unsupported class name!');
|
||||
$cond = array("$indexCol=:id");
|
||||
$params = array('id' => $id);
|
||||
if($indexCol2 && $id2)
|
||||
{
|
||||
$cond[] = "$indexCol2=:id2";
|
||||
$params['id2'] = $id2;
|
||||
}
|
||||
$cond = implode(' AND ', $cond);
|
||||
$sql = "SELECT * FROM $tableName WHERE $cond";
|
||||
return $this->dbClient->selectObject($sql, $params, $className);
|
||||
}
|
||||
|
||||
|
||||
public function updateRow(Daemon_Scyzoryk_DbRow $row)
|
||||
{
|
||||
$row->validate();
|
||||
$className = get_class($row);
|
||||
$tableName = constant("$className::TABLE_NAME");
|
||||
$indexCol = constant("$className::INDEX_COL");
|
||||
$indexCol2 = constant("$className::INDEX_COL2");
|
||||
if(!$tableName || !$indexCol)
|
||||
throw new InvalidArgumentException('This table must be edited manually!');
|
||||
$cols = array();
|
||||
$vals = array();
|
||||
$mods = array();
|
||||
$params = array();
|
||||
$ignore = array($indexCol, $indexCol2);
|
||||
foreach($row as $col => $val)
|
||||
{
|
||||
$cols[] = $col;
|
||||
$vals[] = ":$col";
|
||||
if(!in_array($col, $ignore))
|
||||
$mods[] = "$col=:$col";
|
||||
$params[$col] = $val;
|
||||
}
|
||||
$cols = implode(', ', $cols);
|
||||
$vals = implode(', ', $vals);
|
||||
$mods = implode(', ', $mods);
|
||||
if($mods)
|
||||
$sql = "INSERT INTO $tableName ($cols) VALUES ($vals) ON DUPLICATE KEY UPDATE $mods";
|
||||
else $sql = "REPLACE INTO $tableName ($cols) VALUES ($vals)";
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
}
|
235
2013/daemon/lib/daemon/scyzoryk/browser.php
Normal file
235
2013/daemon/lib/daemon/scyzoryk/browser.php
Normal file
|
@ -0,0 +1,235 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Scyzoryk_Browser extends Daemon_Scyzoryk
|
||||
{
|
||||
|
||||
|
||||
public function findRow($tableName, $indexCol, $id, $name)
|
||||
{
|
||||
$sql = "SELECT $indexCol AS id, name FROM $tableName
|
||||
WHERE $indexCol LIKE CONCAT('%', :id, '%') AND name LIKE CONCAT('%', :name, '%')";
|
||||
$params = array('id' => $id, 'name' => $name);
|
||||
return $this->dbClient->selectAll($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
public function getCombatUnits(Daemon_Scyzoryk_Filter $filter = null)
|
||||
{
|
||||
$cond = array();
|
||||
$params = array();
|
||||
if($filter instanceof Daemon_Scyzoryk_Filter)
|
||||
{
|
||||
if($filter->id)
|
||||
{
|
||||
$cond[] = "combat_unit_id LIKE CONCAT('%', :id, '%')";
|
||||
$params['id'] = $filter->id;
|
||||
}
|
||||
if($filter->name)
|
||||
{
|
||||
$cond[] = "name LIKE CONCAT('%', :name, '%')";
|
||||
$params['name'] = $filter->name;
|
||||
}
|
||||
}
|
||||
$cond = $cond ? 'WHERE '.implode(' AND ', $cond) : null;
|
||||
$sql = "SELECT *, (combat_unit_id LIKE 'character-%') AS _character
|
||||
FROM combat_units $cond ORDER BY _character, combat_unit_id";
|
||||
return $this->dbClient->selectAll($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
public function getFactionRanks($factionId)
|
||||
{
|
||||
$sql = "SELECT * FROM faction_ranks r LEFT JOIN titles USING(title_id) WHERE r.faction_id=:id ORDER BY rank_id";
|
||||
return $this->dbClient->selectAll($sql, array('id' => $factionId));
|
||||
}
|
||||
|
||||
|
||||
public function getFactions()
|
||||
{
|
||||
$sql = "SELECT * FROM factions ORDER BY faction_id";
|
||||
return $this->dbClient->selectAll($sql, array());
|
||||
}
|
||||
|
||||
|
||||
public function getItems(Daemon_Scyzoryk_Filter $filter)
|
||||
{
|
||||
$cond = array();
|
||||
$params = array();
|
||||
if($filter->id)
|
||||
{
|
||||
$cond[] = "item_id LIKE CONCAT('%', :id, '%')";
|
||||
$params['id'] = $filter->id;
|
||||
}
|
||||
if($filter->name)
|
||||
{
|
||||
$cond[] = "name LIKE CONCAT('%', :name, '%')";
|
||||
$params['name'] = $filter->name;
|
||||
}
|
||||
if($filter->type)
|
||||
{
|
||||
$cond[] = 'type = :type';
|
||||
$params['type'] = $filter->type;
|
||||
}
|
||||
$cond = $cond ? 'WHERE '.implode(' AND ', $cond) : null;
|
||||
$sql = "SELECT * FROM items $cond
|
||||
ORDER BY type, damage_type, suggested_value, value, item_id";
|
||||
return $this->dbClient->selectAll($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
public function getItemTemplates()
|
||||
{
|
||||
$sql = "SELECT * FROM item_templates ORDER BY id";
|
||||
return $this->dbClient->selectAll($sql, array());
|
||||
}
|
||||
|
||||
|
||||
public function getLocationEvents($locationId)
|
||||
{
|
||||
$sql = "SELECT * FROM location_events
|
||||
WHERE location_id=:id ORDER BY event_id";
|
||||
return $this->dbClient->selectAll($sql, array('id' => $locationId));
|
||||
}
|
||||
|
||||
|
||||
public function getLocationMonsters($locationId)
|
||||
{
|
||||
$sql = "SELECT l.*, m.name AS monster_name
|
||||
FROM location_monsters l
|
||||
LEFT JOIN monsters m USING(monster_id)
|
||||
WHERE l.location_id=:id ORDER BY l.monster_id";
|
||||
return $this->dbClient->selectAll($sql, array('id' => $locationId));
|
||||
}
|
||||
|
||||
|
||||
public function getLocationPaths($locationId)
|
||||
{
|
||||
$sql = "SELECT p.*, loc.name AS destination_name
|
||||
FROM location_paths p
|
||||
LEFT JOIN locations loc ON p.destination_id = loc.location_id
|
||||
WHERE p.location_id=:id ORDER BY p.destination_id";
|
||||
return $this->dbClient->selectAll($sql, array('id' => $locationId));
|
||||
}
|
||||
|
||||
|
||||
public function getLocationServices($locationId)
|
||||
{
|
||||
$sql = "SELECT l.*, s.name AS service_name, s.type AS service_type
|
||||
FROM location_services l
|
||||
LEFT JOIN services s USING(service_id)
|
||||
WHERE l.location_id=:id ORDER BY s.service_id";
|
||||
return $this->dbClient->selectAll($sql, array('id' => $locationId));
|
||||
}
|
||||
|
||||
|
||||
public function getLocations(Daemon_Scyzoryk_Filter $filter)
|
||||
{
|
||||
$cond = array();
|
||||
$params = array();
|
||||
if($filter->id)
|
||||
{
|
||||
$cond[] = "l.location_id LIKE CONCAT('%', :id, '%')";
|
||||
$params['id'] = $filter->id;
|
||||
}
|
||||
if($filter->name)
|
||||
{
|
||||
$cond[] = "l.name LIKE CONCAT('%', :name, '%')";
|
||||
$params['name'] = $filter->name;
|
||||
}
|
||||
if($filter->region_id)
|
||||
{
|
||||
$cond[] = 'l.region_id = :region_id';
|
||||
$params['region_id'] = $filter->region_id;
|
||||
}
|
||||
$cond = $cond ? 'WHERE '.implode(' AND ', $cond) : null;
|
||||
$sql = "SELECT l.*, r.name AS region_name,
|
||||
( SELECT GROUP_CONCAT(lp.destination_id SEPARATOR ',')
|
||||
FROM location_paths lp WHERE lp.location_id=l.location_id ) AS paths,
|
||||
( SELECT GROUP_CONCAT(lm.monster_id SEPARATOR ',')
|
||||
FROM location_monsters lm WHERE lm.location_id=l.location_id ) AS monsters
|
||||
FROM locations l LEFT JOIN regions r USING(region_id) $cond ORDER BY l.region_id, l.location_id";
|
||||
$data = $this->dbClient->selectAll($sql, $params);
|
||||
foreach ($data as &$row)
|
||||
{
|
||||
$row['paths'] = explode(',', $row['paths']);
|
||||
$row['monsters'] = explode(',', $row['monsters']);
|
||||
}
|
||||
return $data;
|
||||
}
|
||||
|
||||
|
||||
public function getMaps()
|
||||
{
|
||||
$sql = "SELECT * FROM maps ORDER BY sort, map_id";
|
||||
return $this->dbClient->selectAll($sql, array());
|
||||
}
|
||||
|
||||
|
||||
public function getMonsterDrops($monsterId)
|
||||
{
|
||||
$sql = "SELECT m.*, i.name FROM monster_drops m LEFT JOIN items i USING(item_id) WHERE m.monster_id=:id";
|
||||
return $this->dbClient->selectAll($sql, array('id' => $monsterId));
|
||||
}
|
||||
|
||||
|
||||
public function getMonsters(Daemon_Scyzoryk_Filter $filter)
|
||||
{
|
||||
$cond = array();
|
||||
$params = array();
|
||||
if($filter->id)
|
||||
{
|
||||
$cond[] = "m.monster_id LIKE CONCAT('%', :id, '%')";
|
||||
$params['id'] = $filter->id;
|
||||
}
|
||||
if($filter->name)
|
||||
{
|
||||
$cond[] = "m.name LIKE CONCAT('%', :name, '%')";
|
||||
$params['name'] = $filter->name;
|
||||
}
|
||||
if($filter->class)
|
||||
{
|
||||
$cond[] = "m.class = :class";
|
||||
$params['class'] = $filter->class;
|
||||
}
|
||||
$cond = $cond ? 'WHERE '.implode(' AND ', $cond) : null;
|
||||
$sql = "SELECT m.*, ( SELECT GROUP_CONCAT(md.item_id SEPARATOR ', ')
|
||||
FROM monster_drops md WHERE md.monster_id=m.monster_id ) AS drops
|
||||
FROM monsters m $cond ORDER BY m.level, m.monster_id";
|
||||
$data = $this->dbClient->selectAll($sql, $params);
|
||||
foreach ($data as &$row)
|
||||
$row['drops'] = explode(',', $row['drops']);
|
||||
return $data;
|
||||
}
|
||||
|
||||
|
||||
public function getRegions()
|
||||
{
|
||||
$sql = "SELECT r.*, l.name AS respawn_name
|
||||
FROM regions r LEFT JOIN locations l ON l.location_id = r.respawn_id
|
||||
ORDER BY r.region_id";
|
||||
return $this->dbClient->selectAll($sql, array());
|
||||
}
|
||||
|
||||
|
||||
public function getServiceItems($serviceId)
|
||||
{
|
||||
$sql = "SELECT s.*, i.name, s.type='drop' AS _drop
|
||||
FROM service_items s LEFT JOIN items i USING(item_id)
|
||||
WHERE s.service_id=:id ORDER BY type, item_id";
|
||||
return $this->dbClient->selectAll($sql, array('id' => $serviceId));
|
||||
}
|
||||
|
||||
|
||||
public function getServices()
|
||||
{
|
||||
$sql = "SELECT * FROM services ORDER BY service_id";
|
||||
return $this->dbClient->selectAll($sql, array());
|
||||
}
|
||||
|
||||
|
||||
public function getTitles()
|
||||
{
|
||||
$sql = "SELECT * FROM titles ORDER BY title_id";
|
||||
return $this->dbClient->selectAll($sql, array());
|
||||
}
|
||||
}
|
81
2013/daemon/lib/daemon/scyzoryk/controller.php
Normal file
81
2013/daemon/lib/daemon/scyzoryk/controller.php
Normal file
|
@ -0,0 +1,81 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Scyzoryk_Controller
|
||||
{
|
||||
//global objects
|
||||
protected $cfg;
|
||||
protected $browser;
|
||||
protected $dbClient;
|
||||
protected $editor;
|
||||
protected $view;
|
||||
//execution parameters
|
||||
protected $editId = null;
|
||||
protected $editId2 = null;
|
||||
//output parameters
|
||||
protected $pageSubtitle = null;
|
||||
protected $pageSubtitleDetails = null;
|
||||
protected $pageTemplatePath;
|
||||
|
||||
|
||||
final public function __construct(Daemon_Config $cfg)
|
||||
{
|
||||
$this->cfg = $cfg;
|
||||
session_name($this->cfg->sessionName);
|
||||
session_cache_limiter(null);
|
||||
session_start();
|
||||
$this->dbClient = Daemon::createDbClient($this->cfg);
|
||||
$this->browser = new Daemon_Scyzoryk_Browser($this->dbClient);
|
||||
$this->editor = new Daemon_Scyzoryk_Editor($this->dbClient);
|
||||
$this->view = new Daemon_View($this->cfg);
|
||||
$this->editId = isset($_GET['id']) ? $_GET['id'] : null;
|
||||
$this->editId2 = isset($_GET['id2']) ? $_GET['id2'] : null;
|
||||
}
|
||||
|
||||
|
||||
//checks last action's timestamp
|
||||
final private function checkActionTimestamp()
|
||||
{
|
||||
$lastAction = isset($_SESSION['ts']) ? $_SESSION['ts'] : 0.0;
|
||||
$_SESSION['ts'] = microtime(true);
|
||||
return (bool) ($_SESSION['ts'] >= $lastAction + $this->cfg->tsDelta);
|
||||
}
|
||||
|
||||
|
||||
final public function execute()
|
||||
{
|
||||
//prepare controller
|
||||
$this->prepareModel();
|
||||
//check last action's timestamp
|
||||
if($_POST && !$this->checkActionTimestamp())
|
||||
{
|
||||
Daemon_MsgQueue::add('Operacja anulowana: za duża częstość.');
|
||||
$_POST = array();
|
||||
}
|
||||
//execute commands
|
||||
$cmdExecuted = (bool) $this->runCommands();
|
||||
//display page
|
||||
$this->prepareView();
|
||||
$this->view->setPageTitle($this->pageSubtitle, $this->pageSubtitleDetails, $cmdExecuted);
|
||||
$this->view->setMessages(Daemon_MsgQueue::getAll());
|
||||
$this->view->display($this->pageTemplatePath, Daemon_View::MODE_HTML);
|
||||
}
|
||||
|
||||
|
||||
//page-specific
|
||||
protected function prepareModel()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
//page-specific
|
||||
protected function prepareView()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
//page-specific
|
||||
protected function runCommands()
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
151
2013/daemon/lib/daemon/scyzoryk/dbrow.php
Normal file
151
2013/daemon/lib/daemon/scyzoryk/dbrow.php
Normal file
|
@ -0,0 +1,151 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = null;
|
||||
const INDEX_COL = null;
|
||||
const INDEX_COL2 = null;
|
||||
final public function __construct($params = null)
|
||||
{
|
||||
foreach((array) $params as $name => $value)
|
||||
if(property_exists($this, $name))
|
||||
$this->$name = Daemon::normalizeString($value, true);
|
||||
$this->validate();
|
||||
}
|
||||
public function validate() {}
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowFaction extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'factions';
|
||||
const INDEX_COL = 'faction_id';
|
||||
public $faction_id;
|
||||
public $name;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowFactionRank extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'faction_ranks';
|
||||
const INDEX_COL = 'faction_id';
|
||||
const INDEX_COL2 = 'rank_id';
|
||||
public $faction_id;
|
||||
public $rank_id;
|
||||
public $min_points = 1;
|
||||
public $title_id = null;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowLocationEvent extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'location_events';
|
||||
const INDEX_COL = 'location_id';
|
||||
const INDEX_COL2 = 'event_id';
|
||||
public $location_id;
|
||||
public $event_id;
|
||||
public $chance = 1;
|
||||
public $params = '';
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowLocationMonster extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'location_monsters';
|
||||
const INDEX_COL = 'location_id';
|
||||
const INDEX_COL2 = 'monster_id';
|
||||
public $location_id;
|
||||
public $monster_id;
|
||||
public $chance = 1;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowLocationPath extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'location_paths';
|
||||
const INDEX_COL = 'location_id';
|
||||
const INDEX_COL2 = 'destination_id';
|
||||
public $location_id;
|
||||
public $destination_id;
|
||||
public $name = null;
|
||||
public $cost_gold = 0;
|
||||
public $cost_mana = 0;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowLocationService extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'location_services';
|
||||
const INDEX_COL = 'location_id';
|
||||
const INDEX_COL2 = 'service_id';
|
||||
public $location_id;
|
||||
public $service_id;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowMap extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'maps';
|
||||
const INDEX_COL = 'map_id';
|
||||
public $map_id;
|
||||
public $name;
|
||||
public $url = '';
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowMonsterDrop extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'monster_drops';
|
||||
const INDEX_COL = 'monster_id';
|
||||
const INDEX_COL2 = 'item_id';
|
||||
public $monster_id;
|
||||
public $item_id;
|
||||
public $chance = 1;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowRegion extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'regions';
|
||||
const INDEX_COL = 'region_id';
|
||||
public $region_id;
|
||||
public $name;
|
||||
public $respawn_id = null;
|
||||
public $picture_url = null;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowService extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'services';
|
||||
const INDEX_COL = 'service_id';
|
||||
public $service_id;
|
||||
public $name;
|
||||
public $type = 'npc';
|
||||
public $faction_id;
|
||||
public $rank_id;
|
||||
public $description = null;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowServiceItem extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'service_items';
|
||||
const INDEX_COL = 'service_id';
|
||||
const INDEX_COL2 = 'item_id';
|
||||
public $service_id;
|
||||
public $item_id;
|
||||
public $type = 'normal';
|
||||
public $quantity = null;
|
||||
}
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_DbRowTitle extends Daemon_Scyzoryk_DbRow
|
||||
{
|
||||
const TABLE_NAME = 'titles';
|
||||
const INDEX_COL = 'title_id';
|
||||
public $title_id;
|
||||
public $name_f = '';
|
||||
public $name_m = '';
|
||||
public $name_n = '';
|
||||
}
|
139
2013/daemon/lib/daemon/scyzoryk/editor.php
Normal file
139
2013/daemon/lib/daemon/scyzoryk/editor.php
Normal file
|
@ -0,0 +1,139 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Scyzoryk_Editor extends Daemon_Scyzoryk
|
||||
{
|
||||
|
||||
|
||||
public function deleteCombatUnits(array $ids)
|
||||
{
|
||||
$this->deleteRows('combat_units', 'combat_unit_id', $ids);
|
||||
}
|
||||
|
||||
|
||||
public function deleteFactionRanks($factionId, array $ids)
|
||||
{
|
||||
$sql = "DELETE FROM faction_ranks WHERE faction_id=:factionId AND rank_id=:id";
|
||||
foreach($ids as $id)
|
||||
$this->dbClient->query($sql, array('factionId' => $factionId, 'id' => $id));
|
||||
}
|
||||
|
||||
|
||||
public function deleteFactions(array $ids)
|
||||
{
|
||||
$this->deleteRows('factions', 'faction_id', $ids);
|
||||
$this->deleteRows('faction_ranks', 'faction_id', $ids);
|
||||
}
|
||||
|
||||
|
||||
public function deleteItems(array $ids)
|
||||
{
|
||||
$this->deleteRows('items', 'item_id', $ids);
|
||||
$this->deleteRows('service_items', 'item_id', $ids);
|
||||
$this->deleteRows('monster_drops', 'item_id', $ids);
|
||||
}
|
||||
|
||||
|
||||
public function deleteItemTemplates(array $ids)
|
||||
{
|
||||
$this->deleteRows('item_templates', 'id', $ids);
|
||||
}
|
||||
|
||||
|
||||
public function deleteLocationEvents($locationId, array $ids)
|
||||
{
|
||||
$sql = "DELETE FROM location_events WHERE location_id=:locationId AND event_id=:id";
|
||||
foreach($ids as $id)
|
||||
$this->dbClient->query($sql, array('locationId' => $locationId, 'id' => $id));
|
||||
}
|
||||
|
||||
|
||||
public function deleteLocationMonsters($locationId, array $ids)
|
||||
{
|
||||
$sql = "DELETE FROM location_monsters WHERE location_id=:locationId AND monster_id=:id";
|
||||
foreach($ids as $id)
|
||||
$this->dbClient->query($sql, array('locationId' => $locationId, 'id' => $id));
|
||||
}
|
||||
|
||||
|
||||
public function deleteLocationPaths($srcId, array $dst, array $rev = array())
|
||||
{
|
||||
$sql = "DELETE FROM location_paths WHERE location_id=:src AND destination_id=:dst";
|
||||
foreach($dst as $key => $id)
|
||||
{
|
||||
$this->dbClient->query($sql, array('src' => $srcId, 'dst' => $id));
|
||||
if(!empty($rev[$key]))
|
||||
$this->dbClient->query($sql, array('src' => $id, 'dst' => $srcId));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function deleteLocationServices($locationId, array $ids)
|
||||
{
|
||||
$sql = "DELETE FROM location_services WHERE location_id=:locationId AND service_id=:id";
|
||||
foreach($ids as $id)
|
||||
$this->dbClient->query($sql, array('locationId' => $locationId, 'id' => $id));
|
||||
}
|
||||
|
||||
|
||||
public function deleteLocations(array $ids)
|
||||
{
|
||||
$this->deleteRows('locations', 'location_id', $ids);
|
||||
$this->deleteRows('location_events', 'location_id', $ids);
|
||||
$this->deleteRows('location_monsters', 'location_id', $ids);
|
||||
$this->deleteRows('location_paths', 'location_id', $ids);
|
||||
$this->deleteRows('location_paths', 'destination_id', $ids);
|
||||
$this->deleteRows('location_services', 'location_id', $ids);
|
||||
}
|
||||
|
||||
|
||||
public function deleteMaps(array $ids)
|
||||
{
|
||||
$this->deleteRows('maps', 'map_id', $ids);
|
||||
}
|
||||
|
||||
|
||||
public function deleteMonsterDrops($monsterId, array $ids)
|
||||
{
|
||||
$sql = "DELETE FROM monster_drops WHERE monster_id=:monsterId AND item_id=:id";
|
||||
foreach($ids as $id)
|
||||
$this->dbClient->query($sql, array('monsterId' => $monsterId, 'id' => $id));
|
||||
}
|
||||
|
||||
|
||||
public function deleteMonsters(array $ids)
|
||||
{
|
||||
$this->deleteRows('monsters', 'monster_id', $ids);
|
||||
$this->deleteRows('monster_drops', 'monster_id', $ids);
|
||||
$this->deleteRows('location_monsters', 'monster_id', $ids);
|
||||
}
|
||||
|
||||
|
||||
public function deleteRegions(array $ids)
|
||||
{
|
||||
$this->deleteRows('regions', 'region_id', $ids);
|
||||
$sql = "UPDATE locations SET region_id = null WHERE region_id=:id";
|
||||
foreach($ids as $id)
|
||||
$this->dbClient->query($sql, array('id' => $id));
|
||||
}
|
||||
|
||||
|
||||
public function deleteServiceItems($serviceId, array $ids)
|
||||
{
|
||||
$sql = "DELETE FROM service_items WHERE service_id=:serviceId AND item_id=:id";
|
||||
foreach($ids as $id)
|
||||
$this->dbClient->query($sql, array('serviceId' => $serviceId, 'id' => $id));
|
||||
}
|
||||
|
||||
|
||||
public function deleteServices(array $ids)
|
||||
{
|
||||
$this->deleteRows('services', 'service_id', $ids);
|
||||
$this->deleteRows('service_items', 'service_id', $ids);
|
||||
}
|
||||
|
||||
|
||||
public function deleteTitles(array $ids)
|
||||
{
|
||||
$this->deleteRows('titles', 'title_id', $ids);
|
||||
}
|
||||
}
|
43
2013/daemon/lib/daemon/scyzoryk/filter.php
Normal file
43
2013/daemon/lib/daemon/scyzoryk/filter.php
Normal file
|
@ -0,0 +1,43 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Scyzoryk_Filter extends stdClass
|
||||
{
|
||||
const SESSION_VARNAME = 'scf';
|
||||
private $cols;
|
||||
private $data;
|
||||
|
||||
|
||||
public function __construct($name, array $extraCols = array(), $noSession = false)
|
||||
{
|
||||
$this->cols = array_merge(array('id', 'name'), (array) $extraCols);
|
||||
if(!isset($_SESSION[self::SESSION_VARNAME][$name]))
|
||||
$_SESSION[self::SESSION_VARNAME][$name] = array();
|
||||
if(!$noSession)
|
||||
$this->data = & $_SESSION[self::SESSION_VARNAME][$name];
|
||||
else $this->data = array();
|
||||
}
|
||||
|
||||
|
||||
public function __get($name)
|
||||
{
|
||||
return isset($this->data[$name]) ? $this->data[$name] : null;
|
||||
}
|
||||
|
||||
|
||||
public function __isset($name)
|
||||
{
|
||||
return in_array($name, $this->cols) ? true : isset($this->data[$name]);
|
||||
}
|
||||
|
||||
|
||||
public function __set($name, $value)
|
||||
{
|
||||
$this->data[$name] = $value;
|
||||
}
|
||||
|
||||
|
||||
public function __unset($name)
|
||||
{
|
||||
unset($this->data[$name]);
|
||||
}
|
||||
}
|
47
2013/daemon/lib/daemon/service.php
Normal file
47
2013/daemon/lib/daemon/service.php
Normal file
|
@ -0,0 +1,47 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
abstract class Daemon_Service
|
||||
{
|
||||
protected $characterData;
|
||||
protected $dbClient;
|
||||
protected $view;
|
||||
protected $isCommand = false;
|
||||
protected $eventLog = null;
|
||||
protected $bankEnabled = false;
|
||||
protected $templeEnabled = false;
|
||||
|
||||
|
||||
final public function __construct(Daemon_DbClient $dbClient,
|
||||
Daemon_DbObject_CharacterData $characterData, Daemon_View $view,
|
||||
array $serviceData, $bankEnabled, $templeEnabled)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
$this->characterData = $characterData;
|
||||
$this->view = $view;
|
||||
$this->serviceData = $serviceData;
|
||||
$this->bankEnabled = $bankEnabled;
|
||||
$this->templeEnabled = $templeEnabled;
|
||||
}
|
||||
|
||||
|
||||
final protected function clearEvent()
|
||||
{
|
||||
$this->characterData->setLocationEvent(array());
|
||||
$this->characterData->put();
|
||||
}
|
||||
|
||||
|
||||
final public function getEventLog()
|
||||
{
|
||||
return $this->eventLog;
|
||||
}
|
||||
|
||||
|
||||
final public function isCommand()
|
||||
{
|
||||
return $this->isCommand;
|
||||
}
|
||||
|
||||
|
||||
abstract public function execute($params);
|
||||
}
|
95
2013/daemon/lib/daemon/service/bank.php
Normal file
95
2013/daemon/lib/daemon/service/bank.php
Normal file
|
@ -0,0 +1,95 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Service_Bank extends Daemon_Service
|
||||
{
|
||||
const STORAGE_LIMIT = 5;//base limit
|
||||
|
||||
|
||||
public function execute($params)
|
||||
{
|
||||
$inventory = new Daemon_Inventory($this->dbClient, $this->characterData);
|
||||
//run commands
|
||||
$this->isCommand = $this->runCommands($params);
|
||||
//generate output
|
||||
$items = $inventory->getItems('inventory', true);
|
||||
$storage = $inventory->getItems('storage');
|
||||
$storageLimit = $this->getStorageLimit();
|
||||
$this->view->goldBank = $this->characterData->gold_bank;
|
||||
$this->view->goldPurse = $this->characterData->gold_purse;
|
||||
$this->view->inventory = $items;
|
||||
$this->view->storage = $storage;
|
||||
$this->view->storageLimit = $storageLimit;
|
||||
$this->view->storageFull = (count($storage) >= $storageLimit);
|
||||
ob_start();
|
||||
$this->view->display('service/bank.xml');
|
||||
$this->eventLog = ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
private function runCommands($params)
|
||||
{
|
||||
//gold operations
|
||||
if(isset($params['getGold'], $params['putGold']))
|
||||
{
|
||||
$this->goldOperations($params['getGold'], $params['putGold']);
|
||||
return true;
|
||||
}
|
||||
//item operations
|
||||
if(isset($params['getItem']))
|
||||
{
|
||||
$this->getItem($params['getItem']);
|
||||
return true;
|
||||
}
|
||||
if(isset($params['putItem']))
|
||||
{
|
||||
$this->putItem($params['putItem']);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//fetches item from storage
|
||||
private function getItem($inventoryId)
|
||||
{
|
||||
$sql = "UPDATE inventory SET status='inventory' WHERE inventory_id=:id AND character_id=:charId";
|
||||
$params = array('id' => $inventoryId, 'charId' => $this->characterData->character_id);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
private function getStorageLimit()
|
||||
{
|
||||
return self::STORAGE_LIMIT + max(0, floor(log($this->characterData->level)));
|
||||
}
|
||||
|
||||
|
||||
//puts item into storage
|
||||
private function putItem($inventoryId)
|
||||
{
|
||||
$sql = "SELECT COUNT(1) FROM inventory WHERE character_id=:charId AND status='storage'";
|
||||
$n = $this->dbClient->selectValue($sql, array('charId' => $this->characterData->character_id));
|
||||
if($n < $this->getStorageLimit())
|
||||
{
|
||||
$sql = "UPDATE inventory SET status='storage' WHERE inventory_id=:id AND character_id=:charId AND equipped IS NULL";
|
||||
$params = array('id' => $inventoryId, 'charId' => $this->characterData->character_id);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
else Daemon_MsgQueue::add('Twój schowek jest pełny.');
|
||||
}
|
||||
|
||||
|
||||
private function goldOperations($getGold, $putGold)
|
||||
{
|
||||
//get gold
|
||||
$delta = max(0, min((int) $getGold, $this->characterData->gold_bank));
|
||||
$this->characterData->gold_purse += $delta;
|
||||
$this->characterData->gold_bank -= $delta;
|
||||
//put gold
|
||||
$delta = max(0, min((int) $putGold, $this->characterData->gold_purse));
|
||||
$this->characterData->gold_bank += $delta;
|
||||
$this->characterData->gold_purse -= $delta;
|
||||
//store mods
|
||||
$this->characterData->put();
|
||||
}
|
||||
}
|
86
2013/daemon/lib/daemon/service/healer.php
Normal file
86
2013/daemon/lib/daemon/service/healer.php
Normal file
|
@ -0,0 +1,86 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Service_Healer extends Daemon_Service
|
||||
{
|
||||
private $deltaHealthMin = 10;
|
||||
private $deltaHealthMax = 15;
|
||||
private $deltaManaMin = 5;
|
||||
private $deltaManaMax = 10;
|
||||
|
||||
|
||||
public function execute($params)
|
||||
{
|
||||
$this->setParams();
|
||||
//run commands
|
||||
$this->isCommand = $this->runCommands($params);
|
||||
//generate output
|
||||
ob_start();
|
||||
$this->view->characterData = $this->characterData;
|
||||
$this->view->bankEnabled = $this->bankEnabled;
|
||||
$this->view->deltaHealthMin = $this->deltaHealthMin;
|
||||
$this->view->deltaHealthMax = $this->deltaHealthMax;
|
||||
$this->view->deltaManaMin = $this->deltaManaMin;
|
||||
$this->view->deltaManaMax = $this->deltaManaMax;
|
||||
$this->view->display('service/healer.xml');
|
||||
$this->eventLog = ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
private function runCommands($params)
|
||||
{
|
||||
if(isset($params['heal']))
|
||||
{
|
||||
$this->heal($params['heal'], $this->bankEnabled);
|
||||
return true;
|
||||
}
|
||||
if(isset($params['rest']))
|
||||
{
|
||||
$this->rest();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//heals a random amount of health and mana
|
||||
public function heal($gold, $bankEnabled)
|
||||
{
|
||||
if (!$this->characterData->payGold($gold, $bankEnabled))
|
||||
return false;
|
||||
$this->characterData->health += mt_rand($gold * $this->deltaHealthMin, $gold * $this->deltaHealthMax);
|
||||
$this->characterData->mana += mt_rand($gold * $this->deltaManaMin, $gold * $this->deltaManaMax);
|
||||
if($this->characterData->health > $this->characterData->health_max)
|
||||
$this->characterData->health = $this->characterData->health_max;
|
||||
if($this->characterData->mana > $this->characterData->mana_max)
|
||||
$this->characterData->mana = $this->characterData->mana_max;
|
||||
$this->characterData->put();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
public function setParams()
|
||||
{
|
||||
$dbCfg = new Daemon_DbConfig($this->dbClient);
|
||||
$params = $dbCfg->healer;
|
||||
if(is_scalar($params))
|
||||
$params = explode(',', $params);
|
||||
if(isset($params[0], $params[1], $params[2], $params[3]))
|
||||
{
|
||||
$this->deltaHealthMin = (int) $params[0];
|
||||
$this->deltaHealthMax = (int) $params[1];
|
||||
$this->deltaManaMin = (int) $params[2];
|
||||
$this->deltaManaMax = (int) $params[3];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//rests one turn without events
|
||||
public function rest()
|
||||
{
|
||||
if(!$this->characterData->checkTurnCosts())
|
||||
return false;
|
||||
$this->characterData->regen(true);
|
||||
$this->characterData->put();
|
||||
return true;
|
||||
}
|
||||
}
|
202
2013/daemon/lib/daemon/service/shop.php
Normal file
202
2013/daemon/lib/daemon/service/shop.php
Normal file
|
@ -0,0 +1,202 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Service_Shop extends Daemon_Service
|
||||
{
|
||||
|
||||
|
||||
public function execute($params)
|
||||
{
|
||||
$inventoryObj = new Daemon_Inventory($this->dbClient, $this->characterData);
|
||||
//run commands
|
||||
$this->isCommand = $this->runCommands($params);
|
||||
//generate output
|
||||
$equipment = array();
|
||||
$inventory = array();
|
||||
$items = $inventoryObj->getItems('inventory');
|
||||
foreach($items as $key => $row)
|
||||
{
|
||||
$row['_price'] = ceil($row['item']->value / 2);
|
||||
if($row['equipped'])
|
||||
$equipment[$key] = $row;
|
||||
else $inventory[$key] = $row;
|
||||
}
|
||||
$storage = $this->bankEnabled ? $inventoryObj->getItems('storage') : array();
|
||||
foreach($storage as &$row)
|
||||
$row['_price'] = ceil($row['item']->value / 2);
|
||||
$this->view->shopName = $this->serviceData['name'];
|
||||
$this->view->shopDescription = $this->serviceData['description'];
|
||||
$this->view->goldBank = $this->characterData->gold_bank;
|
||||
$this->view->goldPurse = $this->characterData->gold_purse;
|
||||
$this->view->bankEnabled = $this->bankEnabled;
|
||||
$this->view->equipment = $equipment;
|
||||
$this->view->inventory = $inventory;
|
||||
$this->view->storage = $storage;
|
||||
$this->view->hasItems = ($equipment || $inventory || $storage);
|
||||
$this->view->shopItems = $this->getItems();
|
||||
ob_start();
|
||||
$this->view->display('service/shop.xml');
|
||||
$this->eventLog = ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
private function runCommands($params)
|
||||
{
|
||||
//sell item
|
||||
if(isset($params['sell']))
|
||||
{
|
||||
$this->buyFromCharacter($params['sell']);
|
||||
return true;
|
||||
}
|
||||
//buy item(s)
|
||||
if(isset($params['buy'], $params['amount']))
|
||||
{
|
||||
$this->sellToCharacter($params['buy'], $params['amount'], !empty($params['bind']));
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//buys item from character
|
||||
public function buyFromCharacter(array $ids)
|
||||
{
|
||||
foreach($ids as $inventoryId)
|
||||
{
|
||||
$cond = "inv.inventory_id=:id AND character_id=:charId";
|
||||
$params = array('id' => $inventoryId, 'charId' => $this->characterData->character_id);
|
||||
if(!$this->bankEnabled)
|
||||
$cond .= " AND inv.status!='storage'";
|
||||
$sql = "SELECT i.item_id, i.name, i.value, inv.equipped
|
||||
FROM inventory inv JOIN items i USING(item_id) WHERE $cond";
|
||||
if($item = $this->dbClient->selectRow($sql, $params))
|
||||
{
|
||||
$sql = "DELETE FROM inventory WHERE inventory_id=:id";
|
||||
$this->dbClient->query($sql, array('id' => $inventoryId));
|
||||
$buyPrice = ceil($item['value'] / 2);
|
||||
if($this->bankEnabled)
|
||||
$this->characterData->gold_bank += $buyPrice;
|
||||
else $this->characterData->gold_purse += $buyPrice;
|
||||
$this->characterData->put();
|
||||
//add to shop offer
|
||||
$sql = "INSERT INTO service_items (service_id, item_id, type, quantity)
|
||||
VALUES (:serviceId, :itemId, 'drop', 1) ON DUPLICATE KEY UPDATE quantity = quantity + 1";
|
||||
$params = array('serviceId' => $this->serviceData['service_id'], 'itemId' => $item['item_id']);
|
||||
$this->dbClient->query($sql, $params);
|
||||
Daemon_MsgQueue::add("Sprzedajesz $item[name] za $buyPrice zł.");
|
||||
//update character stats if item was equipped
|
||||
if($item['equipped'])
|
||||
{
|
||||
$this->characterData->resetCombatStats();
|
||||
$this->characterData->put();
|
||||
}
|
||||
}
|
||||
else Daemon_MsgQueue::add('Wybrany przedmiot nie istnieje.');
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//fetches shop's offer, grouped by item type
|
||||
public function getItems()
|
||||
{
|
||||
$result = array();
|
||||
$sql = "SELECT s.item_id, s.type, s.quantity
|
||||
FROM service_items s JOIN items i USING(item_id)
|
||||
WHERE service_id=:id ORDER BY i.type ASC, s.type ASC, i.damage_type ASC, i.name ASC";
|
||||
$params = array('id' => $this->serviceData['service_id']);
|
||||
if($data = $this->dbClient->selectAll($sql, $params))
|
||||
{
|
||||
$characterGold = $this->characterData->gold_purse;
|
||||
if($this->bankEnabled)
|
||||
$characterGold += $this->characterData->gold_bank;
|
||||
foreach($data as $row)
|
||||
{
|
||||
$item = new Daemon_DbObject_Item();
|
||||
$item->attachDbClient($this->dbClient);
|
||||
$item->get(array('item_id' => $row['item_id']));
|
||||
$type = $item->type;
|
||||
$item->_price = $this->sellPrice($item->value, $row['quantity']);
|
||||
$item->_drop = ('normal' != $row['type']);
|
||||
$item->_quantity = $row['quantity'];
|
||||
$item->_canBuy = ($item->_price <= $characterGold);
|
||||
$item->_soldOff = ($item->_drop && ($item->_quantity < 1));
|
||||
if(!empty($this->_flags['temple']))
|
||||
$item->_canBind = ($item->value + $item->_price <= $characterGold);
|
||||
else $item->_canBind = false;
|
||||
$result[$type]['items'][$row['item_id']] = $item;
|
||||
}
|
||||
}
|
||||
$groupNames = Daemon_Dictionary::$equipmentGroups;
|
||||
foreach(array_keys($result) as $key)
|
||||
{
|
||||
if(isset($groupNames[$key]))
|
||||
$result[$key]['name'] = $groupNames[$key];
|
||||
else unset($groupNames[$key]);
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
//calculates item price
|
||||
public function sellPrice($value, $quantity)
|
||||
{
|
||||
if($quantity > 0)
|
||||
{
|
||||
$mult = 1 + 4 * exp(-$quantity / 64);
|
||||
return ceil($value * $mult);
|
||||
}
|
||||
else return $value;
|
||||
}
|
||||
|
||||
|
||||
//sells item to character
|
||||
public function sellToCharacter($itemId, $amount, $bind)
|
||||
{
|
||||
$amount = max(1, $amount);
|
||||
if(!$this->templeEnabled)
|
||||
$bind = false;
|
||||
//fetch item data
|
||||
$sql = "SELECT s.*, i.name, i.value FROM service_items s JOIN items i USING(item_id)
|
||||
WHERE service_id=:serviceId AND item_id=:itemId";
|
||||
$params = array('serviceId' => $this->serviceData['service_id'], 'itemId' => $itemId);
|
||||
$item = $this->dbClient->selectRow($sql, $params);
|
||||
//check availability
|
||||
if(!$item)
|
||||
{
|
||||
Daemon_MsgQueue::add('Wybrany przedmiot nie jest dostępny.');
|
||||
return false;
|
||||
}
|
||||
if(('normal' != $item['type']) && ($amount > $item['quantity']))
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie ma tyle towaru w ofercie.');
|
||||
return false;
|
||||
}
|
||||
//calculate total cost
|
||||
$totalCost = 0;
|
||||
for($i = 0; $i < $amount; ++$i)
|
||||
$totalCost += $this->sellPrice($item['value'], $item['quantity'] - $i);
|
||||
if($bind)
|
||||
$totalCost += $amount * $item['value'];
|
||||
//check character gold
|
||||
if(!$this->characterData->payGold($totalCost, $this->bankEnabled))
|
||||
return false;
|
||||
//update service
|
||||
if('normal' != $item['type'])
|
||||
{
|
||||
$sql = "UPDATE service_items SET quantity = quantity - :amount
|
||||
WHERE service_id=:serviceId AND item_id=:itemId";
|
||||
$params = array('serviceId' => $this->serviceData['service_id'], 'itemId' => $itemId, 'amount' => $amount);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
//update character
|
||||
$sql = "INSERT INTO inventory(character_id, item_id, flags) VALUES (:charId, :itemId, :flags)";
|
||||
$params = array('charId' => $this->characterData->character_id, 'itemId' => $itemId);
|
||||
$params['flags'] = $bind ? 'bound,identified' : 'identified';
|
||||
for($i = 0; $i < $amount; ++$i)
|
||||
$this->dbClient->query($sql, $params);
|
||||
//show message
|
||||
if($amount > 1)
|
||||
Daemon_MsgQueue::add("Kupujesz {$amount}x $item[name] za łączną kwotę $totalCost zł.");
|
||||
else Daemon_MsgQueue::add("Kupujesz $item[name] za $totalCost zł.");
|
||||
return true;
|
||||
}
|
||||
}
|
333
2013/daemon/lib/daemon/service/temple.php
Normal file
333
2013/daemon/lib/daemon/service/temple.php
Normal file
|
@ -0,0 +1,333 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Service_Temple extends Daemon_Service
|
||||
{
|
||||
private $factionId;
|
||||
private $xpForMission;
|
||||
private $xpForRegen;
|
||||
|
||||
|
||||
public function execute($params)
|
||||
{
|
||||
$this->setParams();
|
||||
//run commands
|
||||
$this->isCommand = $this->runCommands($params);
|
||||
//generate output
|
||||
ob_start();
|
||||
$this->view->characterData = $this->characterData;
|
||||
$this->view->bankEnabled = $this->bankEnabled;
|
||||
$this->view->itemsToBind = $this->getItems(false, true);
|
||||
$this->view->itemsToOffer = $this->getItems(true, false);
|
||||
$this->view->lastMission = $this->characterData->getLastMission('completed');
|
||||
$this->view->display('service/temple.xml');
|
||||
$this->eventLog = ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
private function runCommands($params)
|
||||
{
|
||||
//bind item
|
||||
if(isset($params['bind']))
|
||||
{
|
||||
$this->bindItem($params['bind']);
|
||||
return true;
|
||||
}
|
||||
//pray at altar
|
||||
if(isset($params['pray']))
|
||||
{
|
||||
$inventoryId = isset($params['offer']) ? $params['offer'] : null;
|
||||
$this->pray($params['pray'], $inventoryId);
|
||||
return true;
|
||||
}
|
||||
//give up mission
|
||||
if(isset($params['giveUp']))
|
||||
{
|
||||
$this->removeMission();
|
||||
return true;
|
||||
}
|
||||
//check mission
|
||||
$this->checkMission();
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
public function bindItem($inventoryId)
|
||||
{
|
||||
//get item data
|
||||
$sql = "SELECT i.name, i.value FROM inventory inv JOIN items i USING(item_id)
|
||||
WHERE inventory_id=:id AND character_id=:charId AND NOT FIND_IN_SET('bound', inv.flags)";
|
||||
$params = array('id' => $inventoryId, 'charId' => $this->characterData->character_id);
|
||||
$item = $this->dbClient->selectRow($sql, $params);
|
||||
if(!$item)
|
||||
{
|
||||
Daemon_MsgQueue::add('Wybrany przedmiot nie istnieje albo już jest przypisany.');
|
||||
return false;
|
||||
}
|
||||
//check character gold
|
||||
if(!$this->characterData->payGold($item['value'], $this->bankEnabled))
|
||||
return false;
|
||||
//bind item
|
||||
$sql = "UPDATE inventory SET flags = CONCAT(',bound,', flags) WHERE inventory_id=:id";
|
||||
$params = array('id' => $inventoryId);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//check if the mission is completed
|
||||
public function checkMission()
|
||||
{
|
||||
$inventoryId = null;
|
||||
$char = $this->characterData;
|
||||
$mission = $char->getLastMission('completed');
|
||||
//check conditions
|
||||
if(!$mission)
|
||||
return false;
|
||||
if('completed' != $mission['progress'])
|
||||
return false;
|
||||
if($this->serviceData['service_id'] != $mission['service_id'])
|
||||
return false;
|
||||
//give xp & gold
|
||||
$rewardXp = ceil(sqrt($char->xp_used));
|
||||
$rewardGold = mt_rand(10 * $rewardXp, 15 * $rewardXp);
|
||||
$char->xp_free += $rewardXp;
|
||||
if($this->bankEnabled)
|
||||
$char->gold_bank += $rewardGold;
|
||||
else $char->gold_purse += $rewardGold;
|
||||
$message = "Misja wykonana. Doświadczenie +$rewardXp, złoto +$rewardGold.";
|
||||
//give skill
|
||||
$skillNames = Daemon_Dictionary::$characterSkills;
|
||||
foreach(array_keys($skillNames) as $key)
|
||||
{
|
||||
$name = "s_$key";
|
||||
if($char->$name)
|
||||
unset($skillNames[$key]);
|
||||
}
|
||||
if(isset($skillNames['preg']) && ($char->xp_used >= $this->xpForRegen))
|
||||
$skill = 'preg';
|
||||
else //random other skill
|
||||
{
|
||||
unset($skillNames['preg']);
|
||||
$skill = array_rand($skillNames);
|
||||
}
|
||||
if($skill)
|
||||
{
|
||||
$skillName = $skillNames[$skill];
|
||||
$message .= " Poznajesz nową umiejętność: $skillName.";
|
||||
$name = "s_$skill";
|
||||
$char->$name = 1;
|
||||
}
|
||||
//join faction or raise reputation
|
||||
if($this->serviceData['faction_id'])
|
||||
$char->improveReputation($this->serviceData['faction_id'], mt_rand(4,6));
|
||||
//save character & mission
|
||||
$char->put();
|
||||
$sql = "UPDATE character_statistics SET missions=missions+1 WHERE character_id=:id";
|
||||
$this->dbClient->query($sql, array('id' => $char->character_id));
|
||||
$sql = "UPDATE character_missions SET progress='rewarded'
|
||||
WHERE character_id=:cid AND rollover_id=:rid";
|
||||
$params = array('cid' => $char->character_id, 'rid' => $mission['rollover_id']);
|
||||
$this->dbClient->query($sql, $params);
|
||||
Daemon_MsgQueue::add($message);
|
||||
}
|
||||
|
||||
|
||||
//returns a list of unbound items
|
||||
public function getItems($withoutEquipped = false, $withoutBound = false)
|
||||
{
|
||||
$result = array();
|
||||
$cond = "character_id=:id";
|
||||
if($withoutEquipped)
|
||||
$cond .= " AND inv.equipped IS NULL";
|
||||
if($withoutBound)
|
||||
$cond .= " AND NOT FIND_IN_SET('bound', inv.flags)";
|
||||
if(!$this->bankEnabled)
|
||||
$cond .= " AND status!='storage'";
|
||||
$sql = "SELECT inv.*, i.name, i.value FROM inventory inv JOIN items i USING(item_id)
|
||||
WHERE $cond ORDER BY i.name, inv.inventory_id";
|
||||
$params = array('id' => $this->characterData->character_id);
|
||||
foreach($this->dbClient->selectAll($sql, $params) as $row)
|
||||
{
|
||||
$flags = $row['flags']
|
||||
? array_fill_keys(explode(',', $row['flags']), true)
|
||||
: array();
|
||||
$status = $row['status'];
|
||||
if(('inventory' == $status) && $row['equipped'])
|
||||
$status = 'equipment';
|
||||
$result[$status][$row['inventory_id']] = array(
|
||||
'name' => $row['name'], 'value' => $row['value'], 'flags' => $flags);
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
//gives mission if its allowed
|
||||
private function giveMission()
|
||||
{
|
||||
$char = $this->characterData;
|
||||
$lastMission = $char->getLastMission('rewarded');
|
||||
//check character's xp
|
||||
if($char->xp_used < $this->xpForMission)
|
||||
{
|
||||
switch($char->_gender)
|
||||
{
|
||||
case 'm': $weak = 'słaby'; break;
|
||||
case 'k': $weak = 'słaba'; break;
|
||||
default: $weak = 'słabe';
|
||||
}
|
||||
Daemon_MsgQueue::add(
|
||||
"Słyszysz głos z nieba:"
|
||||
." \"Twa gorliwość jest godna pochwały, lecz jesteś jeszcze za $weak"
|
||||
." - wróć gdy osiągniesz $this->xpForMission doświadczenia.\""
|
||||
);
|
||||
return false;
|
||||
}
|
||||
//check last mission
|
||||
$sql = "SELECT MAX(rollover_id) FROM rollovers";
|
||||
$lastRollover = $this->dbClient->selectValue($sql);
|
||||
if (empty($lastRollover))
|
||||
{
|
||||
Daemon_MsgQueue::add(
|
||||
'Słyszysz głos z nieba:'
|
||||
.' "Twa gorliwość jest godna pochwały, lecz jeszcze za wcześnie na misje. Wróć później."'
|
||||
);
|
||||
return false;
|
||||
}
|
||||
if($lastRollover && $lastMission && ($lastRollover <= $lastMission['rollover_id']))
|
||||
{
|
||||
switch($char->_gender)
|
||||
{
|
||||
case 'm': $x = 'wykonałeś'; break;
|
||||
case 'k': $x = 'wykonałaś'; break;
|
||||
default: $x = 'wykonałeś';
|
||||
}
|
||||
Daemon_MsgQueue::add(
|
||||
"Słyszysz głos z nieba:"
|
||||
." \"Twa gorliwość jest godna pochwały, lecz $x już dzisiaj misję. Wróć później."
|
||||
);
|
||||
return false;
|
||||
}
|
||||
//get character's region
|
||||
$sql = "SELECT region_id FROM locations WHERE location_id=:id";
|
||||
$regionId = $this->dbClient->selectValue($sql, array('id' => $char->location_id));
|
||||
//find monster near character's level & location
|
||||
$cols = "m.monster_id, m.name";
|
||||
$tables = "monsters m JOIN location_monsters lm USING(monster_id) JOIN locations l USING(location_id)";
|
||||
$params = array('regionId' => $regionId, 'level' => $char->level);
|
||||
$sql = "SELECT $cols FROM $tables
|
||||
WHERE l.region_id=:regionId AND m.level>=:level AND lm.chance > 0
|
||||
ORDER BY level ASC, RAND() LIMIT 1";
|
||||
$monster = $this->dbClient->selectRow($sql, $params);
|
||||
if(!$monster)
|
||||
{
|
||||
$sql = "SELECT $cols FROM $tables
|
||||
WHERE l.region_id=:regionId AND m.level<:level AND lm.chance > 0
|
||||
ORDER BY level DESC, RAND() LIMIT 1";
|
||||
$monster = $this->dbClient->selectRow($sql, $params);
|
||||
}
|
||||
if(!$monster)
|
||||
return false;
|
||||
//get random drop from that monster
|
||||
$sql = "SELECT i.item_id, i.name, md.chance*RAND() AS ord
|
||||
FROM items i JOIN monster_drops md USING(item_id)
|
||||
WHERE md.monster_id=:id AND md.chance > 0 ORDER BY ord LIMIT 1";
|
||||
$params = array('id' => $monster['monster_id']);
|
||||
$item = $this->dbClient->selectRow($sql, $params);
|
||||
//choose mission type
|
||||
if($item && (mt_rand(0,255) < 128))
|
||||
{
|
||||
$missionType = 'item';
|
||||
$missionParams = $item['item_id'];
|
||||
$message = "Przynieś mi przedmiot - $item[name] - a twój wysiłek zostanie nagrodzony.";
|
||||
}
|
||||
else
|
||||
{
|
||||
$missionType = 'monster';
|
||||
$missionParams = $monster['monster_id'];
|
||||
$message = "Pokonaj potwora - $monster[name] - a twój wysiłek zostanie nagrodzony.";
|
||||
}
|
||||
$sql = "INSERT INTO character_missions(character_id, rollover_id, service_id, type, params)
|
||||
VALUES (:cid, :rid, :sid, :type, :params)";
|
||||
$params = array('cid' => $char->character_id, 'rid' => $lastRollover,
|
||||
'sid' => $this->serviceData['service_id'], 'type' => $missionType, 'params' => $missionParams);
|
||||
$this->dbClient->query($sql, $params);
|
||||
Daemon_MsgQueue::add("Słyszysz głos z nieba: \"$message\"");
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//pray at altar, offering gold
|
||||
public function pray($gold, $inventoryId)
|
||||
{
|
||||
$char = $this->characterData;
|
||||
$mission = $char->getLastMission('active');
|
||||
$gold = ceil(abs($gold));
|
||||
//check character gold
|
||||
if(!$char->payGold($gold, $this->bankEnabled))
|
||||
return false;
|
||||
//check item for value and mission
|
||||
$cond = "inv.character_id=:charId AND inv.inventory_id=:inventoryId";
|
||||
if(!$this->bankEnabled)
|
||||
$cond .= " AND inv.status!='storage'";
|
||||
$sql = "SELECT inv.item_id, i.value FROM inventory inv JOIN items i USING(item_id) WHERE $cond";
|
||||
$params = array('charId' => $char->character_id, 'inventoryId' => $inventoryId);
|
||||
$item = $this->dbClient->selectRow($sql, $params);
|
||||
if($item)
|
||||
{
|
||||
$gold += $item['value'];
|
||||
//check for mission target
|
||||
if(($this->serviceData['service_id'] == $mission['service_id']) && ('item' == $mission['type'])
|
||||
&& ($item['item_id'] == $mission['params']) && ('completed' != $mission['progress']))
|
||||
{
|
||||
$mission['progress'] = 1;
|
||||
$sql = "UPDATE character_missions SET progress='completed'
|
||||
WHERE character_id=:cid AND rollover_id=:rid";
|
||||
$params = array('cid' => $char->character_id, 'rid' => $mission['rollover_id']);
|
||||
$this->dbClient->query($sql, $params);
|
||||
}
|
||||
//remove item
|
||||
$sql = "DELETE FROM inventory WHERE inventory_id=:id";
|
||||
$this->dbClient->query($sql, array('id' => $inventoryId));
|
||||
$char->resetCombatStats();
|
||||
}
|
||||
//check for reaction
|
||||
if(!$mission['progress'])
|
||||
{
|
||||
$wealth = $gold + $char->gold_purse + $char->gold_bank;
|
||||
if($wealth)
|
||||
$chance = round(2560 * $gold / $wealth);
|
||||
else $chance = 0;
|
||||
$d256 = mt_rand(0, 255);
|
||||
if($chance <= $d256)
|
||||
{
|
||||
Daemon_msgQueue::add('Twa ofiara nie wywołała żadnej reakcji.');
|
||||
return false;
|
||||
}
|
||||
}
|
||||
//heal character & give mission
|
||||
$char->health = $char->health_max;
|
||||
$char->mana = $char->mana_max;
|
||||
Daemon_MsgQueue::add('Stwórca przyjął ofiarę. Twoje rany zostały uleczone a siły odnowione.');
|
||||
if($mission['progress'])
|
||||
$this->checkMission();
|
||||
else $this->giveMission();
|
||||
//save character
|
||||
$this->characterData->put();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//removes mission
|
||||
public function removeMission()
|
||||
{
|
||||
$sql = "DELETE FROM character_missions WHERE character_id=:id AND progress < 'completed'";
|
||||
$this->dbClient->query($sql, array('id' => $this->characterData->character_id));
|
||||
}
|
||||
|
||||
|
||||
public function setParams()
|
||||
{
|
||||
$dbCfg = new Daemon_DbConfig($this->dbClient);
|
||||
$this->xpForMission = max(0, (int) $dbCfg->templeXpForMission);
|
||||
$this->xpForRegen = max(0, (int) $dbCfg->templeXpForRegen);
|
||||
}
|
||||
}
|
63
2013/daemon/lib/daemon/spell.php
Normal file
63
2013/daemon/lib/daemon/spell.php
Normal file
|
@ -0,0 +1,63 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Spell
|
||||
{
|
||||
private $characterData = null;
|
||||
private $usageLog;
|
||||
|
||||
|
||||
public function attachCharacterData(Daemon_DbObject_CharacterData $characterData)
|
||||
{
|
||||
$this->characterData = $characterData;
|
||||
}
|
||||
|
||||
|
||||
public function attachDbClient(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
public function getUsageLog()
|
||||
{
|
||||
return $this->usageLog;
|
||||
}
|
||||
|
||||
|
||||
public function execute(Daemon_View $view, $spellId)
|
||||
{
|
||||
//fetch spell info
|
||||
$sql = "SELECT name, handle FROM spells WHERE spell_id=:id";
|
||||
$spell = $this->dbClient->selectRow($sql, array('id' => $spellId));
|
||||
if(!$spell)
|
||||
$spell = array('name' => '???', 'handle' => null);
|
||||
//get spell's cost
|
||||
$cost = null;
|
||||
foreach($this->characterData->getSpells() as $row)
|
||||
{
|
||||
if($row['spell_id'] == $spellId)
|
||||
$cost = $row['_cost'];
|
||||
}
|
||||
if(!$cost)
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie znasz tego zaklęcia.');
|
||||
return false;
|
||||
}
|
||||
//check if handler is implemented
|
||||
$className = "Daemon_Spell_$spell[handle]";
|
||||
if(class_exists($className, true) && is_subclass_of($className, 'Daemon_SpellInterface'))
|
||||
{
|
||||
//valid spell, execute it
|
||||
$handler = new $className($this->dbClient, $this->characterData, $view);
|
||||
$this->usageLog = $handler->execute($spellId, $cost);
|
||||
$this->characterData->put();
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
//no effect
|
||||
Daemon_MsgQueue::add("Nieznany efekt: $spell[name]");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
15
2013/daemon/lib/daemon/spell/identify.php
Normal file
15
2013/daemon/lib/daemon/spell/identify.php
Normal file
|
@ -0,0 +1,15 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Spell_Identify extends Daemon_SpellInterface
|
||||
{
|
||||
|
||||
public function execute($spellId, $cost)
|
||||
{
|
||||
if(!$this->updateCharacterMana($cost))
|
||||
return null;
|
||||
$sql = "UPDATE inventory SET flags=CONCAT(flags, ',identified') WHERE character_id=:id AND status!='storage'";
|
||||
$this->dbClient->query($sql, array('id' => $this->characterData->character_id));
|
||||
Daemon_MsgQueue::add('Zawartość plecaka została zidentyfikowana.');
|
||||
return null;
|
||||
}
|
||||
}
|
69
2013/daemon/lib/daemon/spell/scancharacter.php
Normal file
69
2013/daemon/lib/daemon/spell/scancharacter.php
Normal file
|
@ -0,0 +1,69 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Spell_ScanCharacter extends Daemon_SpellInterface
|
||||
{
|
||||
public function execute($spellId, $cost)
|
||||
{
|
||||
$result = null;
|
||||
$target = isset($_POST['target']) ? $_POST['target'] : null;
|
||||
if($target)
|
||||
{
|
||||
if(!$this->updateCharacterMana($cost))
|
||||
return null;
|
||||
$result['char'] = $this->getCharacterByName($target);
|
||||
if($result['char']->character_id)
|
||||
{
|
||||
$result['cdata'] = $result['char']->getCharacterData();
|
||||
if($result['cdata']->level)
|
||||
$chance = $this->characterData->level / ($this->characterData->level + $result['cdata']->level);
|
||||
else $chance = 0;
|
||||
if(mt_rand(0, 255) < 256 * $chance)
|
||||
{
|
||||
$result['equipment'] = $this->getEquipmentByCharacterId($result['char']->character_id);
|
||||
$result['locationName'] = $this->getLocationNameById($result['cdata']->location_id);
|
||||
}
|
||||
else
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie udało się rzucić zaklęcia!');
|
||||
$result = null;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Daemon_MsgQueue::add('Dziwne... zaklęcie niczego nie wskazuje...');
|
||||
$result = null;
|
||||
}
|
||||
}
|
||||
$this->view->spellId = $spellId;
|
||||
$this->view->cost = $cost;
|
||||
$this->view->target = $target;
|
||||
$this->view->result = $result;
|
||||
ob_start();
|
||||
$this->view->display('spell/scancharacter.xml');
|
||||
return ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
private function getCharacterByName($name)
|
||||
{
|
||||
$char = new Daemon_DbObject_Character();
|
||||
$char->attachDbClient($this->dbClient);
|
||||
$char->get(array('name' => $name), true);
|
||||
return $char;
|
||||
}
|
||||
|
||||
|
||||
private function getEquipmentByCharacterId($charId)
|
||||
{
|
||||
$sql = "SELECT i.name FROM inventory inv JOIN items i USING(item_id)
|
||||
WHERE inv.character_id=:id AND inv.equipped IS NOT NULL ORDER BY i.name";
|
||||
return $this->dbClient->selectColumn($sql, array('id' => $charId));
|
||||
}
|
||||
|
||||
|
||||
private function getLocationNameById($locationId)
|
||||
{
|
||||
$sql = "SELECT name FROM locations WHERE location_id=:id";
|
||||
return $this->dbClient->selectValue($sql, array('id' => $locationId));
|
||||
}
|
||||
}
|
65
2013/daemon/lib/daemon/spell/scanitem.php
Normal file
65
2013/daemon/lib/daemon/spell/scanitem.php
Normal file
|
@ -0,0 +1,65 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Spell_ScanItem extends Daemon_SpellInterface
|
||||
{
|
||||
public function execute($spellId, $cost)
|
||||
{
|
||||
$result = null;
|
||||
$target = isset($_POST['target']) ? $_POST['target'] : null;
|
||||
if($target)
|
||||
{
|
||||
if(!$this->updateCharacterMana($cost))
|
||||
return null;
|
||||
$item = $this->getItemByName($target);
|
||||
if($item->item_id)
|
||||
{
|
||||
$result['item'] = $item;
|
||||
$result['typeName'] = Daemon::getArrayValue(Daemon_Dictionary::$itemTypes, $item->type);
|
||||
$result['damageType'] = Daemon::getArrayValue(Daemon_Dictionary::$itemDamageTypes, $item->damage_type);
|
||||
$result['shops'] = $this->getShopsByItemId($result['item']->item_id);
|
||||
$result['monsters'] = $this->getMonstersByItemId($result['item']->item_id);
|
||||
}
|
||||
else
|
||||
{
|
||||
Daemon_MsgQueue::add('Dziwne... zaklęcie niczego nie wskazuje...');
|
||||
$result = null;
|
||||
}
|
||||
}
|
||||
$this->view->spellId = $spellId;
|
||||
$this->view->cost = $cost;
|
||||
$this->view->target = $target;
|
||||
$this->view->result = $result;
|
||||
ob_start();
|
||||
$this->view->display('spell/scanitem.xml');
|
||||
return ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
private function getItemByName($name)
|
||||
{
|
||||
$item = new Daemon_DbObject_Item();
|
||||
$item->attachDbClient($this->dbClient);
|
||||
$item->get(array('name' => $name), true);
|
||||
return $item;
|
||||
}
|
||||
|
||||
|
||||
private function getMonstersByItemId($itemId)
|
||||
{
|
||||
$sql = "SELECT m.name, m.level FROM monster_drops md JOIN monsters m USING(monster_id)
|
||||
WHERE md.item_id=:id ORDER BY m.name";
|
||||
$data = $this->dbClient->selectAll($sql, array('id' => $itemId));
|
||||
$result = array();
|
||||
foreach($data as $row)
|
||||
$result[] = sprintf('%s (poziom %d)', $row['name'], $row['level']);
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
private function getShopsByItemId($itemId)
|
||||
{
|
||||
$sql = "SELECT s.name FROM service_items si JOIN services s USING(service_id)
|
||||
WHERE si.item_id=:id ORDER BY s.name";
|
||||
return $this->dbClient->selectColumn($sql, array('id' => $itemId));
|
||||
}
|
||||
}
|
93
2013/daemon/lib/daemon/spell/scanmonster.php
Normal file
93
2013/daemon/lib/daemon/spell/scanmonster.php
Normal file
|
@ -0,0 +1,93 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Spell_ScanMonster extends Daemon_SpellInterface
|
||||
{
|
||||
public function execute($spellId, $cost)
|
||||
{
|
||||
$result = null;
|
||||
$target = isset($_POST['target']) ? $_POST['target'] : null;
|
||||
if($target)
|
||||
{
|
||||
if(!$this->updateCharacterMana($cost))
|
||||
return null;
|
||||
$result['monster'] = $this->getMonsterByName($target);
|
||||
if($result['monster']->monster_id)
|
||||
{
|
||||
if($result['monster']->level)
|
||||
$chance = $this->characterData->level / ($this->characterData->level + $result['monster']->level);
|
||||
else $chance = 0;
|
||||
if(mt_rand(0, 255) < 256 * $chance)
|
||||
{
|
||||
$result['title'] = $this->getTitleById($result['monster']->title_id);
|
||||
$result['items'] = $this->getItemsByMonsterId($result['monster']->monster_id);
|
||||
$result['locations'] = $this->getLocationsByMonsterId($result['monster']->monster_id);
|
||||
$result['className'] = Daemon_Dictionary::$monsterClasses[$result['monster']->class];
|
||||
//prepare combat unit
|
||||
$unit = (array) $result['monster']->getCombatUnit(false);
|
||||
$attackTypes = Daemon_Dictionary::$combatAttackTypes;
|
||||
$attackSpecials = Daemon_Dictionary::$combatAttackSpecials;
|
||||
$armorSpecials = Daemon_Dictionary::$combatArmorSpecials;
|
||||
$unit['type1_name'] = $unit['type1'] ? $attackTypes[$unit['type1']] : null;
|
||||
$unit['type2_name'] = $unit['type2'] ? $attackTypes[$unit['type2']] : null;
|
||||
$unit['sp1_name'] = $unit['sp1_type'] ? $attackSpecials[$unit['sp1_type']] : null;
|
||||
$unit['sp2_name'] = $unit['sp2_type'] ? $attackSpecials[$unit['sp2_type']] : null;
|
||||
$unit['armor_sp_name'] = $unit['armor_sp_type'] ? $armorSpecials[$unit['armor_sp_type']] : null;
|
||||
$result['unit'] = $unit;
|
||||
}
|
||||
else
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie udało się rzucić zaklęcia!');
|
||||
$result = null;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Daemon_MsgQueue::add('Dziwne... zaklęcie niczego nie wskazuje...');
|
||||
$result = null;
|
||||
}
|
||||
}
|
||||
$this->view->spellId = $spellId;
|
||||
$this->view->cost = $cost;
|
||||
$this->view->target = $target;
|
||||
$this->view->result = $result;
|
||||
ob_start();
|
||||
$this->view->display('spell/scanmonster.xml');
|
||||
return ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
private function getItemsByMonsterId($monsterId)
|
||||
{
|
||||
$sql = "SELECT i.name, md.chance FROM monster_drops md JOIN items i USING(item_id)
|
||||
WHERE md.monster_id=:id ORDER BY i.name";
|
||||
$data = $this->dbClient->selectAll($sql, array('id' => $monsterId));
|
||||
$result = array();
|
||||
foreach($data as $row)
|
||||
$result[] = sprintf('%s (częstość %d)', $row['name'], $row['chance']);
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
private function getLocationsByMonsterId($monsterId)
|
||||
{
|
||||
$sql = "SELECT l.name FROM location_monsters lm JOIN locations l USING(location_id)
|
||||
WHERE lm.monster_id=:id ORDER BY l.name";
|
||||
return $this->dbClient->selectColumn($sql, array('id' => $monsterId));
|
||||
}
|
||||
|
||||
|
||||
private function getMonsterByName($name)
|
||||
{
|
||||
$monster = new Daemon_DbObject_Monster();
|
||||
$monster->attachDbClient($this->dbClient);
|
||||
$monster->get(array('name' => $name), true);
|
||||
return $monster;
|
||||
}
|
||||
|
||||
|
||||
private function getTitleById($titleId)
|
||||
{
|
||||
$sql = "SELECT name_f, name_m, name_n FROM titles WHERE title_id=:id";
|
||||
return $this->dbClient->selectRow($sql, array('id' => $titleId));
|
||||
}
|
||||
}
|
56
2013/daemon/lib/daemon/spell/scout.php
Normal file
56
2013/daemon/lib/daemon/spell/scout.php
Normal file
|
@ -0,0 +1,56 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
class Daemon_Spell_Scout extends Daemon_SpellInterface
|
||||
{
|
||||
public function execute($spellId, $cost)
|
||||
{
|
||||
if(!$this->updateCharacterMana($cost))
|
||||
return null;
|
||||
$location = $this->getLocationById($this->characterData->location_id);
|
||||
if(!$location->location_id)
|
||||
{
|
||||
Daemon_MsgQueue::add('Nie da się badać Otchłani!');
|
||||
return null;
|
||||
}
|
||||
$locations = array(0 => $location);
|
||||
$pathIds = $this->getPathsByLocationId($this->characterData->location_id);
|
||||
foreach($pathIds as $id)
|
||||
$locations[] = $this->getLocationById($id);
|
||||
ob_start();
|
||||
$this->view->locations = $locations;
|
||||
$this->view->display('spell/scout.xml');
|
||||
return ob_get_clean();
|
||||
}
|
||||
|
||||
|
||||
private function getLocationById($locationId)
|
||||
{
|
||||
$location = new Daemon_DbObject_Location;
|
||||
$location->attachDbClient($this->dbClient);
|
||||
$location->get(array('location_id' => $locationId));
|
||||
$location->_monsters = array();
|
||||
$location->_events = array();
|
||||
if($location->location_id)
|
||||
{
|
||||
$params = array('id' => $location->location_id);
|
||||
$sql = "SELECT m.name, m.level, lm.chance FROM location_monsters lm JOIN monsters m USING(monster_id)
|
||||
WHERE lm.location_id=:id ORDER BY m.name";
|
||||
foreach($this->dbClient->selectAll($sql, $params) as $row)
|
||||
$location->_monsters[] = sprintf('%s (poziom %d, częstość %d)', $row['name'], $row['level'], $row['chance']);
|
||||
$sql = "SELECT e.name, le.chance FROM location_events le JOIN events e USING(event_id)
|
||||
WHERE le.location_id=:id ORDER BY e.name";
|
||||
foreach($this->dbClient->selectAll($sql, $params) as $row)
|
||||
$location->_events[] = sprintf('%s (specjalne, częstość %d)', $row['name'], $row['chance']);
|
||||
}
|
||||
return $location;
|
||||
}
|
||||
|
||||
|
||||
private function getPathsByLocationId($locationId)
|
||||
{
|
||||
$sql = "SELECT destination_id FROM location_paths p
|
||||
JOIN locations l ON l.location_id = p.destination_id
|
||||
WHERE p.location_id=:id ORDER BY l.name, p.destination_id";
|
||||
return $this->dbClient->selectColumn($sql, array('id' => $locationId));
|
||||
}
|
||||
}
|
32
2013/daemon/lib/daemon/spellinterface.php
Normal file
32
2013/daemon/lib/daemon/spellinterface.php
Normal file
|
@ -0,0 +1,32 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
abstract class Daemon_SpellInterface
|
||||
{
|
||||
protected $characterData;
|
||||
protected $dbClient;
|
||||
protected $view;
|
||||
|
||||
|
||||
final public function __construct(Daemon_DbClient $dbClient,
|
||||
Daemon_DbObject_CharacterData $characterData, Daemon_View $view)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
$this->characterData = $characterData;
|
||||
$this->view = $view;
|
||||
}
|
||||
|
||||
|
||||
abstract public function execute($spellId, $cost);
|
||||
|
||||
|
||||
final public function updateCharacterMana($cost)
|
||||
{
|
||||
if($this->characterData->mana < $cost)
|
||||
{
|
||||
Daemon_MsgQueue::add("Koszt $cost - nie masz tyle many.");
|
||||
return false;
|
||||
}
|
||||
$this->characterData->mana -= $cost;
|
||||
return true;
|
||||
}
|
||||
}
|
233
2013/daemon/lib/daemon/statistics.php
Normal file
233
2013/daemon/lib/daemon/statistics.php
Normal file
|
@ -0,0 +1,233 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//viewer for world statistics (characters, clans etc)
|
||||
class Daemon_Statistics
|
||||
{
|
||||
private $dbClient;
|
||||
private $charactersOrderTypes = array(
|
||||
'name' => array('key' => 'name', 'sort' => 'name ASC', 'from' => 'name >= :from'),
|
||||
'lvl' => array('key' => 'level', 'sort' => 'level DESC', 'from' => 'level <= :from'),
|
||||
'xp' => array('key' => 'xp_used', 'sort' => 'xp_used DESC', 'from' => 'xp_used <= :from'),
|
||||
'fac' => array('key' => 'faction_id', 'sort' => 'faction_id ASC', 'from' => 'faction_id >= :from'),
|
||||
'clan' => array('key' => 'clan_id', 'sort' => 'clan_id ASC', 'from' => 'clan_id >= :from'),
|
||||
'date' => array('key' => 'date_created', 'sort' => 'date_created ASC', 'from' => 'date_created >= :from'),
|
||||
'last' => array('key' => 'last_action', 'sort' => 'last_action DESC', 'from' => 'last_action >= :from'),
|
||||
'win' => array('key' => 'duel_wins', 'sort' => 'duel_wins DESC', 'from' => 'duel_wins <= :from'),
|
||||
'los' => array('key' => 'duel_losses', 'sort' => 'duel_losses DESC', 'from' => 'duel_losses <= :from'),
|
||||
);
|
||||
|
||||
|
||||
public function __construct(Daemon_DbClient $dbClient)
|
||||
{
|
||||
$this->dbClient = $dbClient;
|
||||
}
|
||||
|
||||
|
||||
public function getBattleById($battleId)
|
||||
{
|
||||
$sql = "SELECT b.combat_log, b.type, l.name AS location_name
|
||||
FROM battles b
|
||||
LEFT JOIN locations l USING(location_id)
|
||||
WHERE b.battle_id = :battleId";
|
||||
$params = array('battleId' => $battleId);
|
||||
return $this->dbClient->selectRow($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
public function getBattles($limit, $from)
|
||||
{
|
||||
$params = array('limit' => $limit + 1);
|
||||
$cond = '';
|
||||
if($from)
|
||||
{
|
||||
$cond = 'WHERE battle_id <= :from';
|
||||
$params['from'] = (int) $from;
|
||||
}
|
||||
$sql = "SELECT b.battle_id, b.rollover_id, b.location_id, b.type, l.name AS location_name,
|
||||
IF(b.combat_log IS NULL OR b.combat_log = '', 0, 1) AS log_exists
|
||||
FROM battles b
|
||||
LEFT JOIN locations l USING(location_id)
|
||||
$cond ORDER BY battle_id DESC LIMIT :limit";
|
||||
return $this->getItemList($sql, $params, $limit, 'battle_id');
|
||||
}
|
||||
|
||||
|
||||
//fetches character data by ID
|
||||
public function getCharacterById($characterId)
|
||||
{
|
||||
$params = array('characterId' => $characterId);
|
||||
$sql = "SELECT c.player_id, p.name AS player_name, c.show_player,
|
||||
c.name, c.gender, c.clan_id, cp.level, cp.xp_used,
|
||||
c.avatar_url, c.quote, c.description, date_format(c.date_created, '%Y-%m-%d') AS date_created,
|
||||
cl.name AS clan_name, f.name AS faction_name, COALESCE(cp.rank_id, 0) AS rank_id,
|
||||
CASE c.gender WHEN 'f' THEN frt.name_f WHEN 'm' THEN frt.name_m ELSE frt.name_n END AS rank_name
|
||||
FROM characters c
|
||||
LEFT JOIN players p USING(player_id)
|
||||
LEFT JOIN character_data cp USING(character_id)
|
||||
LEFT JOIN factions f USING(faction_id)
|
||||
LEFT JOIN faction_ranks fr USING(faction_id, rank_id)
|
||||
LEFT JOIN titles frt USING(title_id)
|
||||
LEFT JOIN clans cl USING(clan_id)
|
||||
WHERE character_id = :characterId";
|
||||
if($character = $this->dbClient->selectRow($sql, $params))
|
||||
{
|
||||
$sql = "SELECT CASE c.gender WHEN 'f' THEN t.name_f WHEN 'm' THEN t.name_m WHEN 'n' THEN t.name_n END AS title
|
||||
FROM character_titles ct
|
||||
JOIN characters c ON c.character_id=ct.character_id
|
||||
JOIN titles t ON ct.title_id=t.title_id
|
||||
WHERE ct.character_id = :characterId ORDER BY title ASC";
|
||||
if($titles = $this->dbClient->selectColumn($sql, $params))
|
||||
$character['titles'] = implode(', ', $titles);
|
||||
else $character['titles'] = null;
|
||||
$sql = "SELECT * FROM character_statistics WHERE character_id = :characterId";
|
||||
$character['statistics'] = $this->dbClient->selectRow($sql, $params);
|
||||
}
|
||||
return $character;
|
||||
}
|
||||
|
||||
|
||||
//fetches a list of characters
|
||||
public function getCharacters($limit, $from, $order, $clanId)
|
||||
{
|
||||
if(!isset($this->charactersOrderTypes[$order]))
|
||||
$order = 'xp';
|
||||
$orderParams = $this->charactersOrderTypes[$order];
|
||||
|
||||
$from = explode(',', $from, 2);
|
||||
if(count($from)<2)
|
||||
$from = array();
|
||||
|
||||
$params = array('limit' => $limit + 1);
|
||||
$where = array("$orderParams[key] IS NOT NULL", "c.character_id!=392");
|
||||
if($clanId)
|
||||
{
|
||||
$params['clanId'] = $clanId;
|
||||
$where[] = 'clan_id=:clanId';
|
||||
}
|
||||
if($from)
|
||||
{
|
||||
$params['from'] = $from[1];
|
||||
$params['characterId'] = $from[0];
|
||||
$where[] = "($orderParams[from] AND character_id>= :characterId)";
|
||||
}
|
||||
if($where)
|
||||
$where = 'WHERE ' . implode(' AND ', $where);
|
||||
else $where = '';
|
||||
$orderClause = $orderParams['sort'];
|
||||
$sql = "SELECT c.character_id, c.name, c.clan_id, cp.level, cp.xp_used,
|
||||
cp.faction_id, COALESCE(cp.rank_id, 0) AS rank_id,
|
||||
date_format(c.date_created, '%Y-%m-%d') AS date_created,
|
||||
date_format(c.last_action, '%Y-%m-%d') AS last_action,
|
||||
cs.duel_wins, cs.duel_losses, cs.kills_mob1, cs.kills_mob2, cs.kills_mob3, cs.kills_mob4
|
||||
FROM characters c
|
||||
LEFT JOIN character_data cp USING(character_id)
|
||||
LEFT JOIN character_statistics cs USING(character_id)
|
||||
$where ORDER BY $orderClause, character_id ASC LIMIT :limit";
|
||||
$list = $this->dbClient->selectAll($sql, $params);
|
||||
if(count($list) > $limit)
|
||||
{
|
||||
$next = array_pop($list);
|
||||
$next = sprintf('%s,%s', $next['character_id'], $next[$orderParams['key']]);
|
||||
}
|
||||
else $next = null;
|
||||
return array('list' => $list, 'next' => $next);
|
||||
}
|
||||
|
||||
|
||||
//fetches clan data by ID
|
||||
public function getClanById($clanId)
|
||||
{
|
||||
$params = array('clanId' => $clanId);
|
||||
$sql = "SELECT cl.*, c.name AS leader_name,
|
||||
date_format(cl.date_created, '%Y-%m-%d') AS date_created
|
||||
FROM clans cl LEFT JOIN characters c ON c.character_id=leader_id
|
||||
WHERE cl.clan_id = :clanId";
|
||||
if($clan = $this->dbClient->selectRow($sql, $params))
|
||||
{
|
||||
$sql = "SELECT COUNT(1) FROM characters WHERE clan_id = :clanId";
|
||||
$clan['members'] = $this->dbClient->selectColumn($sql, $params);
|
||||
}
|
||||
return $clan;
|
||||
}
|
||||
|
||||
|
||||
//fetches a list of clans
|
||||
public function getClans($limit, $from)
|
||||
{
|
||||
$params = array('limit' => $limit + 1);
|
||||
$cond = '';
|
||||
if($from)
|
||||
{
|
||||
$cond = 'WHERE cl.clan_id >= :from';
|
||||
$params['from'] = $from;
|
||||
}
|
||||
$sql = "SELECT cl.*, c.name AS leader_name, n.members,
|
||||
date_format(cl.date_created, '%Y-%m-%d') AS date_created
|
||||
FROM clans cl LEFT JOIN characters c ON c.character_id=leader_id
|
||||
LEFT JOIN (
|
||||
SELECT clan_id, COUNT(1) AS members FROM characters WHERE clan_id IS NOT NULL GROUP BY clan_id
|
||||
) AS n ON n.clan_id=cl.clan_id
|
||||
$cond ORDER BY cl.clan_id ASC LIMIT :limit";
|
||||
return $this->getItemList($sql, $params, $limit, 'clan_id');
|
||||
}
|
||||
|
||||
|
||||
//fetches combat log by duelId
|
||||
public function getDuelById($characterId, $duelId)
|
||||
{
|
||||
$sql = "SELECT d.combat_log, ca.name AS attacker_name, cb.name AS defender_name
|
||||
FROM duels d
|
||||
LEFT JOIN characters ca ON ca.character_id=d.attacker_id
|
||||
LEFT JOIN characters cb ON cb.character_id=d.defender_id
|
||||
WHERE d.duel_id = :duelId AND (d.attacker_id=:characterId OR d.defender_id=:characterId)";
|
||||
$params = array('characterId' => $characterId, 'duelId' => $duelId);
|
||||
return $this->dbClient->selectRow($sql, $params);
|
||||
}
|
||||
|
||||
|
||||
//fetches a list of duels, optionally filtered by character
|
||||
public function getDuels($limit, $from, $characterId, $viewerId)
|
||||
{
|
||||
$params = array('limit' => $limit + 1, 'vid1' => $viewerId, 'vid2' => $viewerId);
|
||||
$where = array();
|
||||
if($characterId)
|
||||
{
|
||||
$params['characterId'] = $characterId;
|
||||
$where[] = '(attacker_id=:characterId OR defender_id=:characterId)';
|
||||
}
|
||||
if($from)
|
||||
{
|
||||
$params['from'] = (int) $from;
|
||||
$where[] = 'duel_id <= :from';
|
||||
}
|
||||
if($where)
|
||||
$where = 'WHERE ' . implode(' AND ', $where);
|
||||
else $where = '';
|
||||
$sql = "SELECT d.duel_id,
|
||||
date_format(d.date_added, '%Y-%m-%d %H:%i:%s') AS date_added,
|
||||
d.rollover_id, d.attacker_id, d.defender_id, d.type, d.winner,
|
||||
(
|
||||
d.combat_log IS NOT NULL AND d.combat_log != ''
|
||||
AND (d.attacker_id = :vid1 OR d.defender_id = :vid2)
|
||||
) AS log_exists,
|
||||
ca.name AS attacker_name, cb.name AS defender_name
|
||||
FROM duels d
|
||||
LEFT JOIN characters ca ON ca.character_id=d.attacker_id
|
||||
LEFT JOIN characters cb ON cb.character_id=d.defender_id
|
||||
$where ORDER BY d.duel_id DESC LIMIT :limit";
|
||||
return $this->getItemList($sql, $params, $limit, 'duel_id');
|
||||
}
|
||||
|
||||
|
||||
private function getItemList($sql, array $params, $limit, $indexCol)
|
||||
{
|
||||
$list = $this->dbClient->selectAll($sql, $params);
|
||||
if(count($list) > $limit)
|
||||
{
|
||||
$next = array_pop($list);
|
||||
$next = $next[$indexCol];
|
||||
}
|
||||
else $next = null;
|
||||
return array('list' => $list, 'next' => $next);
|
||||
}
|
||||
}
|
133
2013/daemon/lib/daemon/view.php
Normal file
133
2013/daemon/lib/daemon/view.php
Normal file
|
@ -0,0 +1,133 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
//wrapper for PHPTAL engine
|
||||
require_once'PHPTAL.php';
|
||||
|
||||
|
||||
class Daemon_View_Filter implements PHPTAL_Filter
|
||||
{
|
||||
public function filter($str)
|
||||
{
|
||||
$str = preg_replace('/\s+/u', ' ', $str);
|
||||
return preg_replace('/> /u', ">\n", $str);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class Daemon_View
|
||||
{
|
||||
public $subtitle;
|
||||
public $subtitleDetails;
|
||||
public $titlePrefix;
|
||||
private $applicationTitle; //for setPageTitle()
|
||||
private $filter;
|
||||
private $phptal;
|
||||
const MODE_HTML = PHPTAL::HTML5;
|
||||
const MODE_ATOM = PHPTAL::XML;
|
||||
const PAGING_MAX_ITEMS = 10;
|
||||
|
||||
|
||||
public function __construct(Daemon_Config $cfg)
|
||||
{
|
||||
$this->applicationTitle = $cfg->applicationTitle;
|
||||
$this->phptal = new PHPTAL();
|
||||
$this->phptal->setTemplateRepository(array($cfg->getFilePath('tpl')));
|
||||
$this->phptal->setPhpCodeDestination($cfg->getFilePath('tmp'));
|
||||
$this->filter = new Daemon_View_Filter();
|
||||
if($cfg->minifyHtml)
|
||||
$this->phptal->setPostFilter($this->filter);
|
||||
}
|
||||
|
||||
|
||||
public function __set($name, $value)
|
||||
{
|
||||
$this->phptal->$name = $value;
|
||||
}
|
||||
|
||||
|
||||
//displays page content
|
||||
public function display($templateName, $outputMode = self::MODE_HTML)
|
||||
{
|
||||
if($outputMode != self::MODE_HTML)
|
||||
{
|
||||
$contentType = 'Content-Type:application/atom+xml;charset=UTF-8';
|
||||
$this->phptal->setOutputMode(PHPTAL::XML);
|
||||
}
|
||||
else
|
||||
{
|
||||
$contentType = 'Content-Type:text/html;charset=UTF-8';
|
||||
$this->phptal->setOutputMode(PHPTAL::HTML5);
|
||||
}
|
||||
$this->phptal->setTemplate($templateName);
|
||||
header($contentType);
|
||||
echo $this->phptal->execute();
|
||||
}
|
||||
|
||||
|
||||
//generates channel menu for chat page
|
||||
public function getChatMenu($channels, $channelId = null)
|
||||
{
|
||||
$menu = array();
|
||||
foreach($channels as $key => $row)
|
||||
$menu[] = array('name' => $row['name'], 'url' => ($key != $channelId) ? "?v=$key" : null);
|
||||
return $menu;
|
||||
}
|
||||
|
||||
|
||||
//generates menu for statistics pages
|
||||
public function getStatisticsMenu($type = null)
|
||||
{
|
||||
$menu = array(
|
||||
'status' => array('name' => 'Status', 'url' => 'stats'),
|
||||
'characters' => array('name' => 'Postacie', 'url' => 'stats-characters'),
|
||||
'clans' => array('name' => 'Klany', 'url' => 'stats-clans'),
|
||||
'duels' => array('name' => 'Pojedynki', 'url' => 'stats-duels'),
|
||||
'battles' => array('name' => 'Bitwy', 'url' => 'stats-battles'),
|
||||
);
|
||||
if(isset($menu[$type]))
|
||||
$menu[$type]['url'] = null;
|
||||
return $menu;
|
||||
}
|
||||
|
||||
|
||||
public function setGameHeader($playerId, $activeCharacter = null, $characterData = null, $location = null)
|
||||
{
|
||||
$this->__set('playerId', $playerId);
|
||||
$this->__set('activeCharacter', $activeCharacter);
|
||||
$this->__set('characterData', $characterData);
|
||||
$this->__set('location', $location);
|
||||
}
|
||||
|
||||
|
||||
public function setMessages($messages)
|
||||
{
|
||||
$this->__set('pageMessages', $messages);
|
||||
}
|
||||
|
||||
|
||||
public function setPageSkin($skinId)
|
||||
{
|
||||
$skinDirUrls = Daemon_Dictionary::$skinDirUrls;
|
||||
if (isset($skinDirUrls[$skinId]))
|
||||
$url = $skinDirUrls[$skinId];
|
||||
else
|
||||
$url = array_shift($skinDirUrls);
|
||||
$this->__set('pageSkinName', $skinId);
|
||||
$this->__set('pageSkinUrl', $url);
|
||||
}
|
||||
|
||||
|
||||
public function setPageTitle($subtitle = null, $details = null, $isCommand = false)
|
||||
{
|
||||
$title = $this->applicationTitle;
|
||||
if($subtitle)
|
||||
{
|
||||
if($details)
|
||||
$title = sprintf('%s: %s - %s', $subtitle, $details, $title);
|
||||
else $title = sprintf('%s - %s', $subtitle, $title);
|
||||
}
|
||||
if($isCommand)
|
||||
$title = sprintf('[cmd] %s', $title);
|
||||
$this->__set('pageTitle', $title);
|
||||
}
|
||||
}
|
291
2013/daemon/lib/jsmin.php
Normal file
291
2013/daemon/lib/jsmin.php
Normal file
|
@ -0,0 +1,291 @@
|
|||
<?php
|
||||
/**
|
||||
* jsmin.php - PHP implementation of Douglas Crockford's JSMin.
|
||||
*
|
||||
* This is pretty much a direct port of jsmin.c to PHP with just a few
|
||||
* PHP-specific performance tweaks. Also, whereas jsmin.c reads from stdin and
|
||||
* outputs to stdout, this library accepts a string as input and returns another
|
||||
* string as output.
|
||||
*
|
||||
* PHP 5 or higher is required.
|
||||
*
|
||||
* Permission is hereby granted to use this version of the library under the
|
||||
* same terms as jsmin.c, which has the following license:
|
||||
*
|
||||
* --
|
||||
* Copyright (c) 2002 Douglas Crockford (www.crockford.com)
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
* this software and associated documentation files (the "Software"), to deal in
|
||||
* the Software without restriction, including without limitation the rights to
|
||||
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
|
||||
* of the Software, and to permit persons to whom the Software is furnished to do
|
||||
* so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in all
|
||||
* copies or substantial portions of the Software.
|
||||
*
|
||||
* The Software shall be used for Good, not Evil.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
* --
|
||||
*
|
||||
* @package JSMin
|
||||
* @author Ryan Grove <ryan@wonko.com>
|
||||
* @copyright 2002 Douglas Crockford <douglas@crockford.com> (jsmin.c)
|
||||
* @copyright 2008 Ryan Grove <ryan@wonko.com> (PHP port)
|
||||
* @license http://opensource.org/licenses/mit-license.php MIT License
|
||||
* @version 1.1.1 (2008-03-02)
|
||||
* @link http://code.google.com/p/jsmin-php/
|
||||
*/
|
||||
|
||||
class JSMin {
|
||||
const ORD_LF = 10;
|
||||
const ORD_SPACE = 32;
|
||||
|
||||
protected $a = '';
|
||||
protected $b = '';
|
||||
protected $input = '';
|
||||
protected $inputIndex = 0;
|
||||
protected $inputLength = 0;
|
||||
protected $lookAhead = null;
|
||||
protected $output = '';
|
||||
|
||||
// -- Public Static Methods --------------------------------------------------
|
||||
|
||||
public static function minify($js) {
|
||||
$jsmin = new JSMin($js);
|
||||
return $jsmin->min();
|
||||
}
|
||||
|
||||
// -- Public Instance Methods ------------------------------------------------
|
||||
|
||||
public function __construct($input) {
|
||||
$this->input = str_replace("\r\n", "\n", $input);
|
||||
$this->inputLength = strlen($this->input);
|
||||
}
|
||||
|
||||
// -- Protected Instance Methods ---------------------------------------------
|
||||
|
||||
protected function action($d) {
|
||||
switch($d) {
|
||||
case 1:
|
||||
$this->output .= $this->a;
|
||||
|
||||
case 2:
|
||||
$this->a = $this->b;
|
||||
|
||||
if ($this->a === "'" || $this->a === '"') {
|
||||
for (;;) {
|
||||
$this->output .= $this->a;
|
||||
$this->a = $this->get();
|
||||
|
||||
if ($this->a === $this->b) {
|
||||
break;
|
||||
}
|
||||
|
||||
if (ord($this->a) <= self::ORD_LF) {
|
||||
throw new JSMinException('Unterminated string literal.');
|
||||
}
|
||||
|
||||
if ($this->a === '\\') {
|
||||
$this->output .= $this->a;
|
||||
$this->a = $this->get();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
case 3:
|
||||
$this->b = $this->next();
|
||||
|
||||
if ($this->b === '/' && (
|
||||
$this->a === '(' || $this->a === ',' || $this->a === '=' ||
|
||||
$this->a === ':' || $this->a === '[' || $this->a === '!' ||
|
||||
$this->a === '&' || $this->a === '|' || $this->a === '?')) {
|
||||
|
||||
$this->output .= $this->a . $this->b;
|
||||
|
||||
for (;;) {
|
||||
$this->a = $this->get();
|
||||
|
||||
if ($this->a === '/') {
|
||||
break;
|
||||
} elseif ($this->a === '\\') {
|
||||
$this->output .= $this->a;
|
||||
$this->a = $this->get();
|
||||
} elseif (ord($this->a) <= self::ORD_LF) {
|
||||
throw new JSMinException('Unterminated regular expression '.
|
||||
'literal.');
|
||||
}
|
||||
|
||||
$this->output .= $this->a;
|
||||
}
|
||||
|
||||
$this->b = $this->next();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected function get() {
|
||||
$c = $this->lookAhead;
|
||||
$this->lookAhead = null;
|
||||
|
||||
if ($c === null) {
|
||||
if ($this->inputIndex < $this->inputLength) {
|
||||
$c = $this->input[$this->inputIndex];
|
||||
$this->inputIndex += 1;
|
||||
} else {
|
||||
$c = null;
|
||||
}
|
||||
}
|
||||
|
||||
if ($c === "\r") {
|
||||
return "\n";
|
||||
}
|
||||
|
||||
if ($c === null || $c === "\n" || ord($c) >= self::ORD_SPACE) {
|
||||
return $c;
|
||||
}
|
||||
|
||||
return ' ';
|
||||
}
|
||||
|
||||
protected function isAlphaNum($c) {
|
||||
return ord($c) > 126 || $c === '\\' || preg_match('/^[\w\$]$/', $c) === 1;
|
||||
}
|
||||
|
||||
protected function min() {
|
||||
$this->a = "\n";
|
||||
$this->action(3);
|
||||
|
||||
while ($this->a !== null) {
|
||||
switch ($this->a) {
|
||||
case ' ':
|
||||
if ($this->isAlphaNum($this->b)) {
|
||||
$this->action(1);
|
||||
} else {
|
||||
$this->action(2);
|
||||
}
|
||||
break;
|
||||
|
||||
case "\n":
|
||||
switch ($this->b) {
|
||||
case '{':
|
||||
case '[':
|
||||
case '(':
|
||||
case '+':
|
||||
case '-':
|
||||
$this->action(1);
|
||||
break;
|
||||
|
||||
case ' ':
|
||||
$this->action(3);
|
||||
break;
|
||||
|
||||
default:
|
||||
if ($this->isAlphaNum($this->b)) {
|
||||
$this->action(1);
|
||||
}
|
||||
else {
|
||||
$this->action(2);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
switch ($this->b) {
|
||||
case ' ':
|
||||
if ($this->isAlphaNum($this->a)) {
|
||||
$this->action(1);
|
||||
break;
|
||||
}
|
||||
|
||||
$this->action(3);
|
||||
break;
|
||||
|
||||
case "\n":
|
||||
switch ($this->a) {
|
||||
case '}':
|
||||
case ']':
|
||||
case ')':
|
||||
case '+':
|
||||
case '-':
|
||||
case '"':
|
||||
case "'":
|
||||
$this->action(1);
|
||||
break;
|
||||
|
||||
default:
|
||||
if ($this->isAlphaNum($this->a)) {
|
||||
$this->action(1);
|
||||
}
|
||||
else {
|
||||
$this->action(3);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
$this->action(1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return $this->output;
|
||||
}
|
||||
|
||||
protected function next() {
|
||||
$c = $this->get();
|
||||
|
||||
if ($c === '/') {
|
||||
switch($this->peek()) {
|
||||
case '/':
|
||||
for (;;) {
|
||||
$c = $this->get();
|
||||
|
||||
if (ord($c) <= self::ORD_LF) {
|
||||
return $c;
|
||||
}
|
||||
}
|
||||
|
||||
case '*':
|
||||
$this->get();
|
||||
|
||||
for (;;) {
|
||||
switch($this->get()) {
|
||||
case '*':
|
||||
if ($this->peek() === '/') {
|
||||
$this->get();
|
||||
return ' ';
|
||||
}
|
||||
break;
|
||||
|
||||
case null:
|
||||
throw new JSMinException('Unterminated comment.');
|
||||
}
|
||||
}
|
||||
|
||||
default:
|
||||
return $c;
|
||||
}
|
||||
}
|
||||
|
||||
return $c;
|
||||
}
|
||||
|
||||
protected function peek() {
|
||||
$this->lookAhead = $this->get();
|
||||
return $this->lookAhead;
|
||||
}
|
||||
}
|
||||
|
||||
// -- Exceptions ---------------------------------------------------------------
|
||||
class JSMinException extends Exception {}
|
||||
?>
|
39
2013/daemon/php.ini
Normal file
39
2013/daemon/php.ini
Normal file
|
@ -0,0 +1,39 @@
|
|||
[PHP]
|
||||
; language options
|
||||
short_open_tag = Off
|
||||
asp_tags = Off
|
||||
|
||||
; error handling and logging
|
||||
error_reporting = E_ALL | E_STRICT
|
||||
display_errors = On
|
||||
display_startup_errors = Off
|
||||
log_errors = On
|
||||
log_errors_max_len = 0
|
||||
html_errors = Off
|
||||
error_log = "path/to/error.log"
|
||||
|
||||
; data handling
|
||||
register_globals = Off
|
||||
register_long_arrays = Off
|
||||
register_argc_argv = Off
|
||||
auto_globals_jit = On
|
||||
magic_quotes_gpc = Off
|
||||
magic_quotes_runtime = Off
|
||||
magic_quotes_sybase = Off
|
||||
default_mimetype = "text/plain"
|
||||
default_charset = "UTF-8"
|
||||
always_populate_raw_post_data = Off
|
||||
|
||||
|
||||
[Date]
|
||||
date.timezone = "Europe/Warsaw"
|
||||
|
||||
[iconv]
|
||||
iconv.input_encoding = "UTF-8"
|
||||
iconv.internal_encoding = "UTF-8"
|
||||
iconv.output_encoding = "UTF-8"
|
||||
|
||||
[Session]
|
||||
session.use_cookies = 1
|
||||
session.use_only_cookies = 1
|
||||
session.auto_start = 0
|
10
2013/daemon/public/.htaccess
Normal file
10
2013/daemon/public/.htaccess
Normal file
|
@ -0,0 +1,10 @@
|
|||
DirectoryIndex index.php
|
||||
Redirect gone ./favicon.ico
|
||||
Redirect permanent /help http://pl.daemon.wikia.com/wiki/Daemon_Wiki
|
||||
|
||||
RewriteEngine On
|
||||
|
||||
RewriteCond %{SCRIPT_FILENAME} !-d
|
||||
RewriteCond %{SCRIPT_FILENAME} !-f
|
||||
RewriteCond %{REQUEST_FILENAME}.php -f
|
||||
RewriteRule ^(.*)$ /$1.php [L,QSA]
|
31
2013/daemon/public/_init.php
Normal file
31
2013/daemon/public/_init.php
Normal file
|
@ -0,0 +1,31 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
ignore_user_abort(true);
|
||||
error_reporting(E_ALL|E_STRICT);
|
||||
iconv_set_encoding('internal_encoding', 'UTF-8');
|
||||
mb_internal_encoding('UTF-8');
|
||||
date_default_timezone_set('Europe/Warsaw');
|
||||
setlocale(LC_ALL, 'pl_PL.utf8');
|
||||
|
||||
if (isset($_GET['phpinfo']) && $_GET['phpinfo'] == 'Waaghh!')
|
||||
{
|
||||
header('Content-Type: text/html; charset=UTF-8');
|
||||
phpinfo();
|
||||
exit;
|
||||
}
|
||||
|
||||
if(extension_loaded('zlib') && !ini_get('zlib.output_compression'))
|
||||
ob_start('ob_gzhandler'); //setting zlib.output_compression doesn't work
|
||||
header('Content-Type: text/plain; charset=UTF-8');
|
||||
header('X-UA-Compatible: IE=edge');
|
||||
|
||||
$applicationRoot = realpath(dirname(__FILE__).DIRECTORY_SEPARATOR.'..');
|
||||
set_include_path($applicationRoot.DIRECTORY_SEPARATOR.'lib');
|
||||
require'daemon.php';
|
||||
spl_autoload_register(array('Daemon', 'autoload'));
|
||||
|
||||
Daemon_ErrorHandler::$logDir = $applicationRoot.DIRECTORY_SEPARATOR.'log';
|
||||
set_error_handler(array('Daemon_ErrorHandler', 'errorHandler'));
|
||||
set_exception_handler(array('Daemon_ErrorHandler', 'exceptionHandler'));
|
||||
|
||||
return new Daemon_Config($applicationRoot);
|
63
2013/daemon/public/account.php
Normal file
63
2013/daemon/public/account.php
Normal file
|
@ -0,0 +1,63 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Account extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Konto';
|
||||
protected $pageTemplatePath = 'account.xml';
|
||||
protected $requireAuthentication = true;
|
||||
private $characters;
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->characters = $this->player->getCharacters();
|
||||
//mark active character
|
||||
$activeCharId = $this->player->getCharacterId();
|
||||
if($activeCharId && isset($this->characters[$activeCharId]))
|
||||
$this->characters[$activeCharId]['active'] = true;
|
||||
else $activeCharId = null;
|
||||
//prepare view
|
||||
$this->view->characters = $this->characters;
|
||||
$this->view->genders = Daemon_Dictionary::$genders;
|
||||
$this->view->preview = Daemon::formatMessage($this->activeCharacter->description, true);
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
$turnDelta = $this->dbCfg->turnDelta;
|
||||
$turnLimit = $this->dbCfg->turnLimit;
|
||||
//create character
|
||||
if(isset($_POST['newName'], $_POST['newGender']))
|
||||
{
|
||||
$this->player->addCharacter($_POST['newName'], $_POST['newGender'], $turnDelta, $turnLimit);
|
||||
return true;
|
||||
}
|
||||
//set active character
|
||||
if(isset($_POST['use']))
|
||||
{
|
||||
$this->player->setCharacterId($_POST['use']);
|
||||
$this->activeCharacter = $this->player->getActiveCharacter();
|
||||
$this->characterData = $this->activeCharacter->getCharacterData();
|
||||
$this->activeCharacter->updateLastAction();
|
||||
return true;
|
||||
}
|
||||
//reset or delete character
|
||||
if(isset($_POST['char'], $_POST['action']))
|
||||
{
|
||||
$reset = ($_POST['action'] == 'reset');
|
||||
$this->player->deleteCharacter($_POST['char'], $reset, $turnDelta, $turnLimit);
|
||||
$this->activeCharacter = $this->player->getActiveCharacter();
|
||||
$this->characterData = $this->activeCharacter->getCharacterData();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Account($cfg);
|
||||
$ctrl->execute();
|
46
2013/daemon/public/auth.php
Normal file
46
2013/daemon/public/auth.php
Normal file
|
@ -0,0 +1,46 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Auth extends Daemon_Controller
|
||||
{
|
||||
protected $disableMessages = true;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$url = $this->cfg->applicationUrl;
|
||||
if($this->player->getPlayerId())
|
||||
$url .= 'account';
|
||||
Daemon::redirect($url);
|
||||
exit;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(!$this->dbCfg->loginEnabled)
|
||||
return false;
|
||||
if(isset($_POST['login'], $_POST['pass']))
|
||||
{
|
||||
$this->player->authenticate($_POST['login'], $_POST['pass']);
|
||||
return true;
|
||||
}
|
||||
if(isset($_POST['logout']))
|
||||
{
|
||||
$this->player->unauthenticate();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Auth($cfg);
|
||||
$ctrl->execute();
|
89
2013/daemon/public/character.php
Normal file
89
2013/daemon/public/character.php
Normal file
|
@ -0,0 +1,89 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Character extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Postać';
|
||||
protected $pageTemplatePath = 'character.xml';
|
||||
protected $requireActiveChar = true;
|
||||
protected $requireAuthentication = true;
|
||||
protected $requireNoEvents = true;
|
||||
private $eventLog;
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
if($this->eventLog)
|
||||
{
|
||||
$this->pageSubtitle = 'Użycie zaklęcia';
|
||||
$this->pageTemplatePath = 'event.xml';
|
||||
$this->view->eventLog = $this->eventLog;
|
||||
return;
|
||||
}
|
||||
//prepare attributes list
|
||||
$list = array();
|
||||
foreach(Daemon_Dictionary::$characterAttributes as $key => $name)
|
||||
{
|
||||
$col = "a_$key";
|
||||
$value = $this->characterData->$col;
|
||||
$list[$key] = array('name' => $name, 'value' => $value, 'inc' => ($value <= $this->characterData->xp_free));
|
||||
}
|
||||
$this->view->attributes = $list;
|
||||
//prepare skill list
|
||||
$list = array();
|
||||
foreach(Daemon_Dictionary::$characterSkills as $key => $name)
|
||||
{
|
||||
$col = "s_$key";
|
||||
$value = $this->characterData->$col;
|
||||
$list[$key] = array('name' => $name, 'value' => $value, 'inc' => ($value <= $this->characterData->xp_free));
|
||||
}
|
||||
$this->view->skills = $list;
|
||||
//prepare spell list
|
||||
$this->view->spells = $this->characterData->getSpells();
|
||||
//prepare combat stats
|
||||
$unit = (array) $this->characterData->getCombatUnit();
|
||||
$attackTypes = Daemon_Dictionary::$combatAttackTypes;
|
||||
$attackSpecials = Daemon_Dictionary::$combatAttackSpecials;
|
||||
$armorSpecials = Daemon_Dictionary::$combatArmorSpecials;
|
||||
$unit['type1_name'] = $unit['type1'] ? $attackTypes[$unit['type1']] : null;
|
||||
$unit['type2_name'] = $unit['type2'] ? $attackTypes[$unit['type2']] : null;
|
||||
$unit['sp1_name'] = $unit['sp1_type'] ? $attackSpecials[$unit['sp1_type']] : null;
|
||||
$unit['sp2_name'] = $unit['sp2_type'] ? $attackSpecials[$unit['sp2_type']] : null;
|
||||
$unit['armor_sp_name'] = $unit['armor_sp_type'] ? $armorSpecials[$unit['armor_sp_type']] : null;
|
||||
$this->view->combatStats = $unit;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
//improve attribute
|
||||
if(isset($_POST['incA']))
|
||||
{
|
||||
$this->characterData->improveAttribute($_POST['incA']);
|
||||
return true;
|
||||
}
|
||||
//improve skill
|
||||
if(isset($_POST['incS']))
|
||||
{
|
||||
$this->characterData->improveSkill($_POST['incS']);
|
||||
return true;
|
||||
}
|
||||
//cast spell
|
||||
if(isset($_POST['cast']))
|
||||
{
|
||||
$handler = new Daemon_Spell();
|
||||
$handler->attachCharacterData($this->characterData);
|
||||
$handler->attachDbClient($this->dbClient);
|
||||
$handler->execute($this->view, $_POST['cast']);
|
||||
$this->eventLog = $handler->getUsageLog();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Character($cfg);
|
||||
$ctrl->execute();
|
61
2013/daemon/public/chat.php
Normal file
61
2013/daemon/public/chat.php
Normal file
|
@ -0,0 +1,61 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Chat extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Ogłoszenia';
|
||||
protected $pageTemplatePath = 'chat.xml';
|
||||
private $channelId;
|
||||
private $channels;
|
||||
private $forum;
|
||||
private $writeAccess;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->forum = new Daemon_Forum($this->dbClient);
|
||||
$this->channels = $this->activeCharacter->getForumChannels();
|
||||
$this->channelId = isset($_GET['v']) ? $_GET['v'] : null;
|
||||
if(!isset($this->channels[$this->channelId]))
|
||||
$this->channelId = 'public';
|
||||
$this->writeAccess = !empty($this->channels[$this->channelId]['writable']);
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$listLimit = max(1, (int) $this->dbCfg->listLimitMessages);
|
||||
$listOffset = isset($_GET['n']) ? (int) $_GET['n'] : 0;
|
||||
|
||||
$this->pageSubtitleUseQuery = true;
|
||||
$from = isset($_GET['from']) ? (int) $_GET['from'] : 0;
|
||||
$data = $this->forum->getChat($listLimit, $from, $this->channelId);
|
||||
|
||||
foreach($data['list'] as &$row)
|
||||
$row['content'] = Daemon::formatMessage($row['content'], true);
|
||||
$this->view->inputMsg = isset($_POST['msg']) ? $_POST['msg'] : null;
|
||||
$this->view->list = $data['list'];
|
||||
|
||||
$this->view->menu = $this->view->getChatMenu($this->channels, $this->channelId);
|
||||
$this->view->nextUrl = $data['next'] ? '?from='.urlencode($data['next']) : null;
|
||||
$this->view->channelId = $this->channelId;
|
||||
$this->view->writeAccess = $this->writeAccess;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if($this->writeAccess && isset($_POST['msg']))
|
||||
{
|
||||
$this->forum->addChat($this->player->getCharacterId(), $this->channelId, $_POST['msg']);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Chat($cfg);
|
||||
$ctrl->execute();
|
129
2013/daemon/public/clan.php
Normal file
129
2013/daemon/public/clan.php
Normal file
|
@ -0,0 +1,129 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Page extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Klan';
|
||||
protected $pageTemplatePath = 'clan.xml';
|
||||
protected $requireActiveChar = true;
|
||||
protected $requireAuthentication = true;
|
||||
protected $requireNoEvents = true;
|
||||
private $clan;
|
||||
private $isLeader = false;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->clan = new Daemon_DbObject_Clan;
|
||||
if($this->activeCharacter->clan_id)
|
||||
{
|
||||
$this->clan->attachDbClient($this->dbClient);
|
||||
$this->clan->get(array('clan_id' => $this->activeCharacter->clan_id));
|
||||
if($this->clan->leader_id)
|
||||
$this->isLeader = ($this->clan->leader_id == $this->activeCharacter->character_id);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
if($this->clan->clan_id)
|
||||
$this->prepareViewMember();
|
||||
else $this->prepareViewSolo();
|
||||
}
|
||||
|
||||
|
||||
private function prepareViewMember()
|
||||
{
|
||||
$this->view->clan = $this->clan;
|
||||
$this->view->preview = Daemon::formatMessage($this->clan->description, true);
|
||||
$this->view->isLeader = $this->isLeader;
|
||||
$this->view->members = $this->clan->getMembers($this->activeCharacter->character_id);
|
||||
$invitations = $this->clan->getInvitations();
|
||||
foreach($invitations as &$row)
|
||||
$row['description'] = Daemon::formatMessage($row['description'], true);
|
||||
$this->view->invitations = $invitations;
|
||||
}
|
||||
|
||||
|
||||
private function prepareViewSolo()
|
||||
{
|
||||
$this->view->invitations = $this->activeCharacter->getInvitations();
|
||||
}
|
||||
|
||||
|
||||
public function runCommands()
|
||||
{
|
||||
if($this->clan->clan_id)
|
||||
return $this->runCommandsMember();
|
||||
else return $this->runCommandsSolo();
|
||||
}
|
||||
|
||||
|
||||
private function runCommandsMember()
|
||||
{
|
||||
if($this->isLeader)
|
||||
{
|
||||
if(isset($_POST['accept']))
|
||||
{
|
||||
$forum = new Daemon_Forum($this->dbClient);
|
||||
$this->clan->acceptCharacter($_POST['accept'], $forum);
|
||||
return true;
|
||||
}
|
||||
if(isset($_POST['kick']))
|
||||
{
|
||||
$forum = new Daemon_Forum($this->dbClient);
|
||||
$this->clan->kickMember($_POST['kick'], $forum);
|
||||
return true;
|
||||
}
|
||||
if(isset($_POST['setLeader'], $_POST['desc']))
|
||||
{
|
||||
if($_POST['setLeader'] && ($_POST['setLeader'] != $this->clan->leader_id))
|
||||
{
|
||||
$this->clan->leader_id = $_POST['setLeader'];
|
||||
$this->isLeader = false;
|
||||
}
|
||||
$this->clan->description = $_POST['desc'];
|
||||
$this->clan->put();
|
||||
return true;
|
||||
}
|
||||
if(isset($_POST['disband']))
|
||||
{
|
||||
$this->clan->delete();
|
||||
$this->clan = new Daemon_DbObject_Clan;
|
||||
$this->activeCharacter->clan_id = null;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
if(isset($_POST['leave']))
|
||||
{
|
||||
$this->activeCharacter->clan_id = null;
|
||||
$this->activeCharacter->put();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private function runCommandsSolo()
|
||||
{
|
||||
if(isset($_POST['join'], $_POST['desc']))
|
||||
{
|
||||
$forum = new Daemon_Forum($this->dbClient);
|
||||
$this->activeCharacter->inviteClan($_POST['join'], $_POST['desc'], $forum);
|
||||
return true;
|
||||
}
|
||||
if(isset($_POST['create'], $_POST['id'], $_POST['name']))
|
||||
{
|
||||
$this->activeCharacter->createClan($_POST['id'], $_POST['name']);
|
||||
$this->prepareModel();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Page($cfg);
|
||||
$ctrl->execute();
|
39
2013/daemon/public/duel.php
Normal file
39
2013/daemon/public/duel.php
Normal file
|
@ -0,0 +1,39 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Duel extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Pojedynek';
|
||||
protected $pageTemplatePath = 'duel.xml';
|
||||
protected $requireActiveChar = true;
|
||||
protected $requireAuthentication = true;
|
||||
protected $requireLocation = true;
|
||||
protected $requireNoEvents = true;
|
||||
private $combatLog = null;
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->view->combatLog = $this->combatLog;
|
||||
}
|
||||
|
||||
|
||||
public function runCommands()
|
||||
{
|
||||
//attack
|
||||
if(isset($_POST['attack']))
|
||||
{
|
||||
$this->view->setGameHeader($this->player->getPlayerId(),
|
||||
$this->activeCharacter, $this->characterData, $this->location);
|
||||
$this->combatLog = $this->characterData->attack($this->view, $_POST['attack'], $this->location->type);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Duel($cfg);
|
||||
$ctrl->execute();
|
41
2013/daemon/public/edit-account.php
Normal file
41
2013/daemon/public/edit-account.php
Normal file
|
@ -0,0 +1,41 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Page extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Ustawienia';
|
||||
protected $pageSubtitleDetails = 'konto';
|
||||
protected $pageTemplatePath = 'edit-account.xml';
|
||||
protected $requireAuthentication = true;
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->view->player = $this->player;
|
||||
$this->view->skins = array_keys(Daemon_Dictionary::$skinDirUrls);
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
//update player data
|
||||
if(isset($_POST['name'], $_POST['pass1'], $_POST['pass2'], $_POST['skin'], $_POST['email']))
|
||||
{
|
||||
if($_POST['pass1'] || $_POST['pass2'])
|
||||
$this->player->setPassword($_POST['pass1'], $_POST['pass2']);
|
||||
$_POST['name'] = Daemon::normalizeString($_POST['name']);
|
||||
$this->player->name = $_POST['name'] ? $_POST['name'] : null;
|
||||
$this->player->skin = $_POST['skin'] ? $_POST['skin'] : null;
|
||||
$this->player->email = $_POST['email'] ? $_POST['email'] : null;
|
||||
$this->player->put();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Page($cfg);
|
||||
$ctrl->execute();
|
60
2013/daemon/public/edit-character.php
Normal file
60
2013/daemon/public/edit-character.php
Normal file
|
@ -0,0 +1,60 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Account extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Ustawienia';
|
||||
protected $pageSubtitleDetails = 'postać';
|
||||
protected $pageTemplatePath = 'edit-character.xml';
|
||||
protected $requireAuthentication = true;
|
||||
private $character;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$id = isset($_GET['id']) ? (int) $_GET['id'] : null;
|
||||
$this->character = new Daemon_DbObject_Character;
|
||||
if($id)
|
||||
{
|
||||
$this->character->attachDbClient($this->dbClient);
|
||||
$params = array('character_id' => $id, 'player_id' => $this->player->getPlayerId());
|
||||
$this->character->get($params);
|
||||
}
|
||||
if(!$this->character->character_id)
|
||||
{
|
||||
Daemon_MsgQueue::add('Wybrana postać nie istnieje.');
|
||||
Daemon::redirect($this->cfg->getUrl('map'));
|
||||
exit;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->pageSubtitleDetails = $this->character->name;
|
||||
$this->view->character = $this->character;
|
||||
$this->view->preview = Daemon::formatMessage($this->character->description, true);
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
//update character
|
||||
if(isset($_POST['avatar'], $_POST['quote'], $_POST['desc']))
|
||||
{
|
||||
$this->character->show_player = !empty($_POST['player']);
|
||||
$this->character->avatar_url = $_POST['avatar'];
|
||||
$this->character->quote = $_POST['quote'];
|
||||
$this->character->description = $_POST['desc'];
|
||||
$this->character->put();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Account($cfg);
|
||||
$ctrl->execute();
|
27
2013/daemon/public/index.php
Normal file
27
2013/daemon/public/index.php
Normal file
|
@ -0,0 +1,27 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Index extends Daemon_Controller
|
||||
{
|
||||
protected $pageTemplatePath = 'index.xml';
|
||||
private $news;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->news = new Daemon_News($this->dbClient);
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->view->loginEnabled = (bool) $this->dbCfg->loginEnabled;
|
||||
$this->view->news = $this->news->getEntries(3, false);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Index($cfg);
|
||||
$ctrl->execute();
|
106
2013/daemon/public/inventory.php
Normal file
106
2013/daemon/public/inventory.php
Normal file
|
@ -0,0 +1,106 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Inventory extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Ekwipunek';
|
||||
protected $pageTemplatePath = 'inventory.xml';
|
||||
protected $requireActiveChar = true;
|
||||
protected $requireAuthentication = true;
|
||||
protected $requireNoEvents = true;
|
||||
private $inventory;
|
||||
private $eventLog;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->inventory = new Daemon_Inventory($this->dbClient, $this->characterData);
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
if($this->eventLog)
|
||||
{
|
||||
$this->pageSubtitle = 'Użycie przedmiotu';
|
||||
$this->view->eventLog = $this->eventLog;
|
||||
}
|
||||
else $this->view->eventLog = null;
|
||||
$items = $this->inventory->getItems('inventory');
|
||||
$this->view->equipmentSlots = Daemon_Dictionary::$equipmentSlots;
|
||||
//prepare items
|
||||
$cmdNames = Daemon_Dictionary::$equipmentButtons;
|
||||
foreach($items as &$row)
|
||||
{
|
||||
if($row['equipped'])
|
||||
$cmd = 'unequip';
|
||||
elseif('item' != $row['item']->type)
|
||||
$cmd = 'equip';
|
||||
else $cmd = 'use';
|
||||
if(isset($cmdNames[$cmd]))
|
||||
{
|
||||
$row['item']->_cmdType = $cmd;
|
||||
$row['item']->_cmdName = $cmdNames[$cmd];
|
||||
}
|
||||
else
|
||||
{
|
||||
$row['item']->_cmdType = null;
|
||||
$row['item']->_cmdName = null;
|
||||
}
|
||||
$row['_showSlots'] = ('equip' == $cmd);
|
||||
$row['_slots'] = $row['item']->getSlots();
|
||||
$row['_multiSlots'] = (count($row['_slots']) > 1);
|
||||
}
|
||||
$this->view->items = $this->inventory->groupItemsByType($items);
|
||||
$this->view->equipment = $this->inventory->getEquipment($items);
|
||||
//prepare combat stats
|
||||
$unit = (array) $this->characterData->getCombatUnit();
|
||||
$attackTypes = Daemon_Dictionary::$combatAttackTypes;
|
||||
$attackSpecials = Daemon_Dictionary::$combatAttackSpecials;
|
||||
$armorSpecials = Daemon_Dictionary::$combatArmorSpecials;
|
||||
$unit['type1_name'] = $unit['type1'] ? $attackTypes[$unit['type1']] : null;
|
||||
$unit['type2_name'] = $unit['type2'] ? $attackTypes[$unit['type2']] : null;
|
||||
$unit['sp1_name'] = $unit['sp1_type'] ? $attackSpecials[$unit['sp1_type']] : null;
|
||||
$unit['sp2_name'] = $unit['sp2_type'] ? $attackSpecials[$unit['sp2_type']] : null;
|
||||
$unit['armor_sp_name'] = $unit['armor_sp_type'] ? $armorSpecials[$unit['armor_sp_type']] : null;
|
||||
$this->view->combatStats = $unit;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
//equip item
|
||||
if(isset($_POST['equip'], $_POST['slot']))
|
||||
{
|
||||
$this->inventory->equip($_POST['equip'], $_POST['slot']);
|
||||
$this->characterData->resetCombatStats();
|
||||
$this->characterData->put();
|
||||
return true;
|
||||
}
|
||||
//unequip item
|
||||
if(isset($_POST['unequip']))
|
||||
{
|
||||
$this->inventory->unequip($_POST['unequip']);
|
||||
$this->characterData->resetCombatStats();
|
||||
$this->characterData->put();
|
||||
return true;
|
||||
}
|
||||
//use item
|
||||
if(isset($_POST['use']))
|
||||
{
|
||||
$handler = new Daemon_Item();
|
||||
$handler->attachCharacterData($this->characterData);
|
||||
$handler->attachDbClient($this->dbClient);
|
||||
$handler->execute($this->view, $_POST['use']);
|
||||
$this->eventLog = $handler->getUsageLog();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Inventory($cfg);
|
||||
$ctrl->execute();
|
67
2013/daemon/public/mail.php
Normal file
67
2013/daemon/public/mail.php
Normal file
|
@ -0,0 +1,67 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Chat extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Poczta';
|
||||
protected $pageTemplatePath = 'mail.xml';
|
||||
protected $requireAuthentication = true;
|
||||
private $forum;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->forum = new Daemon_Forum($this->dbClient);
|
||||
if(isset($_GET['to']))
|
||||
$_POST['to'] = $_GET['to'];
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
//fetch mail
|
||||
$listLimit = max(1, (int) $this->dbCfg->listLimitMessages);
|
||||
$listOffset = isset($_GET['n']) ? (int) $_GET['n'] : 0;
|
||||
$characterId = (int) $this->activeCharacter->character_id;
|
||||
|
||||
$this->pageSubtitleUseQuery = true;
|
||||
$from = isset($_GET['from']) ? (int) $_GET['from'] : 0;
|
||||
$data = $this->forum->getMail($listLimit, $from, $characterId);
|
||||
foreach($data['list'] as &$row)
|
||||
$row['content'] = Daemon::formatMessage($row['content'], true);
|
||||
|
||||
//mark as read
|
||||
if($data['list'])
|
||||
{
|
||||
$messageId = $data['list'][0]['message_id'];
|
||||
$sql = "UPDATE characters SET last_mail_id = :messageId WHERE character_id = :characterId";
|
||||
$params = array('characterId' => $characterId, 'messageId' => $messageId);
|
||||
$this->dbClient->query($sql, $params);
|
||||
$this->activeCharacter->last_mail_id = $messageId;
|
||||
}
|
||||
|
||||
//display page
|
||||
$this->view->inputTo = isset($_POST['to']) ? $_POST['to'] : null;
|
||||
$this->view->inputMsg = isset($_POST['msg']) ? $_POST['msg'] : null;
|
||||
$this->view->list = $data['list'];
|
||||
$nextUrl = $data['next'] ? '?from='.urlencode($data['next']) : null;
|
||||
$this->view->nextUrl = $nextUrl;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(isset($_POST['to'], $_POST['msg']))
|
||||
{
|
||||
$this->forum->addMail($this->player->getCharacterId(), $_POST['to'], $_POST['msg']);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Chat($cfg);
|
||||
$ctrl->execute();
|
86
2013/daemon/public/map.php
Normal file
86
2013/daemon/public/map.php
Normal file
|
@ -0,0 +1,86 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Map extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Otoczenie';
|
||||
protected $pageTemplatePath = 'map.xml';
|
||||
protected $requireActiveChar = true;
|
||||
protected $requireAuthentication = true;
|
||||
protected $requireLocation = true;
|
||||
private $eventLog = null;
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
if($this->eventLog)
|
||||
{
|
||||
$this->pageSubtitle = 'Zdarzenie';
|
||||
$this->pageTemplatePath = 'event.xml';
|
||||
$this->view->eventLog = $this->eventLog;
|
||||
return;
|
||||
}
|
||||
$bossStatuses = Daemon_Dictionary::$bossStatuses;
|
||||
if(isset($bossStatuses[$this->location->boss_status]))
|
||||
$this->location->boss_status_name = $bossStatuses[$this->location->boss_status];
|
||||
else
|
||||
$this->location->boss_status_name = null;
|
||||
$this->pageSubtitleDetails = $this->location->name;
|
||||
$this->view->locationDesc = nl2br(htmlspecialchars($this->location->description));
|
||||
$this->view->pictureUrl = $this->location->getPictureUrl();
|
||||
$this->view->region = $this->location->getRegionName();
|
||||
$this->view->faction = $this->location->getFactionName();
|
||||
$this->view->maps = $this->location->getMaps();
|
||||
$this->view->paths = $this->location->getPaths();
|
||||
$this->view->services = $this->location->getServices();
|
||||
$this->view->lastMission = $this->characterData->getLastMission('completed');
|
||||
//prepare character list
|
||||
$showAll = isset($_GET['more']);
|
||||
$halfLimit = $showAll ? null : (int) ceil($this->dbCfg->listLimitCharacters/2);
|
||||
$n = $this->location->getCharacterCount(2*$halfLimit+1);
|
||||
$characters = $this->location->getCharacters($this->characterData, $halfLimit);
|
||||
$this->view->characters = $characters;
|
||||
$this->view->showMoreLink = !$showAll && ($n > 2*$halfLimit);
|
||||
}
|
||||
|
||||
|
||||
public function runCommands()
|
||||
{
|
||||
$isCommand = false;
|
||||
//actions
|
||||
if(isset($_POST['act']))
|
||||
{
|
||||
switch($_POST['act'])
|
||||
{
|
||||
case'train':
|
||||
$this->location->actionTrain();
|
||||
break;
|
||||
case'rest':
|
||||
$this->location->actionRest();
|
||||
break;
|
||||
case'hunt':
|
||||
$this->location->actionHunt();
|
||||
break;
|
||||
}
|
||||
$isCommand = true;
|
||||
}
|
||||
//travel
|
||||
if(isset($_POST['travel']))
|
||||
{
|
||||
$this->location->actionTravel($_POST['travel']);
|
||||
$isCommand = true;
|
||||
}
|
||||
//run events
|
||||
$this->view->setGameHeader($this->player->getPlayerId(),
|
||||
$this->activeCharacter, $this->characterData, $this->location);
|
||||
$this->eventLog = $this->characterData->runEvent($this->view);
|
||||
//set "isCommand" flag
|
||||
return $isCommand;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Map($cfg);
|
||||
$ctrl->execute();
|
33
2013/daemon/public/news.php
Normal file
33
2013/daemon/public/news.php
Normal file
|
@ -0,0 +1,33 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_News extends Daemon_Controller
|
||||
{
|
||||
protected $disablePlayer = true;
|
||||
protected $pageOutputMode = Daemon_View::MODE_ATOM;
|
||||
protected $pageSubtitle = 'Regulamin';
|
||||
protected $pageTemplatePath = 'news.xml';
|
||||
private $news;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->news = new Daemon_News($this->dbClient);
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->view->feedId = $this->cfg->applicationUrl;
|
||||
$this->view->feedUrl = "{$this->cfg->applicationUrl}news";
|
||||
$this->view->feedTitle = $this->cfg->applicationTitle;
|
||||
$this->view->feedUpdated = $this->news->getLastUpdated();
|
||||
$this->view->entries = $this->news->getEntries(10, true);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_News($cfg);
|
||||
$ctrl->execute();
|
6
2013/daemon/public/not-implemented.html
Normal file
6
2013/daemon/public/not-implemented.html
Normal file
|
@ -0,0 +1,6 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<meta charset="utf-8">
|
||||
<title>Błąd</title>
|
||||
<p>Wybrana strona jeszcze nie istnieje.</p>
|
||||
</html>
|
40
2013/daemon/public/register.php
Normal file
40
2013/daemon/public/register.php
Normal file
|
@ -0,0 +1,40 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Register extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Rejestracja';
|
||||
protected $pageTemplatePath = 'register.xml';
|
||||
private $registerEnabled;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->registerEnabled = (bool) $this->dbCfg->registerEnabled;
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->view->registerEnabled = $this->registerEnabled;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(!$this->registerEnabled)
|
||||
Daemon_MsgQueue::add('Rejestracja wyłączona.');
|
||||
elseif(isset($_POST['login'], $_POST['pass'], $_POST['pass2']))
|
||||
{
|
||||
$this->player->register($_POST['login'], $_POST['pass'], $_POST['pass2']);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Register($cfg);
|
||||
$ctrl->execute();
|
38
2013/daemon/public/reset-password.php
Normal file
38
2013/daemon/public/reset-password.php
Normal file
|
@ -0,0 +1,38 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Page extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Reset hasła';
|
||||
protected $pageTemplatePath = 'reset-password.xml';
|
||||
private $registerEnabled;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->registerEnabled = (bool) $this->dbCfg->registerEnabled;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(isset($_POST['login'], $_POST['email'], $_POST['pass'], $_POST['pass2']))
|
||||
{
|
||||
$this->player->preparePasswordReset($_POST['login'], $_POST['email'], $_POST['pass'], $_POST['pass2']);
|
||||
return true;
|
||||
}
|
||||
elseif (isset($_GET['key']))
|
||||
{
|
||||
$this->player->resetPassword($_GET['key']);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Page($cfg);
|
||||
$ctrl->execute();
|
59
2013/daemon/public/respawn.php
Normal file
59
2013/daemon/public/respawn.php
Normal file
|
@ -0,0 +1,59 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Respawn extends Daemon_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Otchłań Narodzin';
|
||||
protected $pageTemplatePath = 'respawn.xml';
|
||||
protected $requireActiveChar = true;
|
||||
protected $requireAuthentication = true;
|
||||
private $defaultRespawn;
|
||||
private $respawns;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
if (empty($this->characterData->xp_used))
|
||||
{
|
||||
Daemon_MsgQueue::add('Pamiętaj by wydać startowe doświadczenie.');
|
||||
Daemon::redirect($this->cfg->getUrl('character'));
|
||||
exit;
|
||||
}
|
||||
$this->defaultRespawn = $this->dbCfg->defaultRespawn;
|
||||
$this->gender = $this->characterData->_gender;
|
||||
if(empty($this->location->location_id))
|
||||
$this->respawns = $this->characterData->getRespawns($this->defaultRespawn);
|
||||
else
|
||||
{
|
||||
Daemon_MsgQueue::add('Już posiadasz powłokę cielesną.');
|
||||
Daemon::redirect($this->cfg->getUrl('map'));
|
||||
exit;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->view->respawns = $this->respawns;
|
||||
$this->view->firstOne = empty($this->characterData->deaths);
|
||||
$this->view->rolloversEnabled = (bool) $this->dbCfg->rolloversEnabled;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(isset($_POST['respawn']))
|
||||
{
|
||||
$this->characterData->respawn($_POST['respawn'], $this->defaultRespawn);
|
||||
Daemon::redirect($this->cfg->getUrl('map'));
|
||||
exit;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Respawn($cfg);
|
||||
$ctrl->execute();
|
2
2013/daemon/public/robots.txt
Normal file
2
2013/daemon/public/robots.txt
Normal file
|
@ -0,0 +1,2 @@
|
|||
User-Agent: *
|
||||
Allow: *
|
21
2013/daemon/public/rules.php
Normal file
21
2013/daemon/public/rules.php
Normal file
|
@ -0,0 +1,21 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'./_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Rules extends Daemon_Controller
|
||||
{
|
||||
protected $disablePlayer = true;
|
||||
protected $pageSubtitle = 'Regulamin';
|
||||
protected $pageTemplatePath = 'rules.xml';
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->view->lastModified = date(DATE_RFC1123, filemtime($this->cfg->getFilePath('tpl', 'rules.xml')));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Rules($cfg);
|
||||
$ctrl->execute();
|
126
2013/daemon/public/scyzoryk/arena.php
Normal file
126
2013/daemon/public/scyzoryk/arena.php
Normal file
|
@ -0,0 +1,126 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'../_init.php';
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_Controller_Page extends Daemon_Scyzoryk_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Arena';
|
||||
protected $pageTemplatePath = 'scyzoryk/arena.xml';
|
||||
private $selectMode;
|
||||
private $combatCount;
|
||||
private $unitIdA;
|
||||
private $unitIdB;
|
||||
private $winsA;
|
||||
private $winsB;
|
||||
private $draws;
|
||||
private $doubleKOs;
|
||||
private $healthSumA;
|
||||
private $healthSumB;
|
||||
private $healthMinA;
|
||||
private $healthMinB;
|
||||
private $healthMaxA;
|
||||
private $healthMaxB;
|
||||
|
||||
|
||||
public function prepareModel()
|
||||
{
|
||||
$this->selectMode = isset($_POST['mode']) ? $_POST['mode'] : null;
|
||||
$this->combatCount = isset($_POST['n']) ? min(500, max(100, (int) $_POST['n'])) : 100;
|
||||
$this->unitIdA = isset($_POST['unitA']) ? $_POST['unitA'] : null;
|
||||
$this->unitIdB = isset($_POST['unitB']) ? $_POST['unitB'] : null;
|
||||
}
|
||||
|
||||
|
||||
public function prepareView()
|
||||
{
|
||||
$this->view->selectMode = $this->selectMode;
|
||||
$this->view->combatCount = $this->combatCount;
|
||||
$this->view->unitIdA = $this->unitIdA;
|
||||
$this->view->unitIdB = $this->unitIdB;
|
||||
$this->view->winsA = round(100 * $this->winsA / $this->combatCount, 2);
|
||||
$this->view->winsB = round(100 * $this->winsB / $this->combatCount, 2);
|
||||
$this->view->draws = round(100 * $this->draws / $this->combatCount, 2);
|
||||
$this->view->doubleKOs = round(100 * $this->doubleKOs / $this->combatCount, 2);
|
||||
$this->view->healthSumA = round(100 * $this->healthSumA / $this->combatCount, 2);
|
||||
$this->view->healthSumB = round(100 * $this->healthSumB / $this->combatCount, 2);
|
||||
$this->view->healthMinA = round(100 * $this->healthMinA, 2);
|
||||
$this->view->healthMinB = round(100 * $this->healthMinB, 2);
|
||||
$this->view->healthMaxA = round(100 * $this->healthMaxA, 2);
|
||||
$this->view->healthMaxB = round(100 * $this->healthMaxB, 2);
|
||||
|
||||
$filter = new Daemon_Scyzoryk_Filter('combat-units');
|
||||
$filter->noChars = false;
|
||||
$unitsC = $unitsM = array();
|
||||
foreach ($this->browser->getCombatUnits($filter) as $row)
|
||||
{
|
||||
if ($row['_character'])
|
||||
$unitsC[] = $row;
|
||||
else
|
||||
$unitsM[] = $row;
|
||||
}
|
||||
$this->view->unitsC = $unitsC;
|
||||
$this->view->unitsM = $unitsM;
|
||||
}
|
||||
|
||||
|
||||
public function runCommands()
|
||||
{
|
||||
if(isset($_POST['attack']))
|
||||
{
|
||||
if(!$this->unitIdA || !$this->unitIdB)
|
||||
{
|
||||
Daemon_MsgQueue::add('Wybierz obie jednostki.');
|
||||
return true;
|
||||
}
|
||||
$this->winsA = 0;
|
||||
$this->winsB = 0;
|
||||
$this->draws = 0;
|
||||
$this->doubleKOs = 0;
|
||||
$this->healthSumA = 0;
|
||||
$this->healthSumB = 0;
|
||||
$unitA = new Daemon_Combat_Unit();
|
||||
$unitA->attachDbClient($this->dbClient);
|
||||
$unitA->get(array('combat_unit_id' => $this->unitIdA));
|
||||
$unitB = new Daemon_Combat_Unit();
|
||||
$unitB->attachDbClient($this->dbClient);
|
||||
$unitB->get(array('combat_unit_id' => $this->unitIdB));
|
||||
$this->healthMinA = 1.0;
|
||||
$this->healthMinB = 1.0;
|
||||
$this->healthMaxA = 0.0;
|
||||
$this->healthMaxB = 0.0;
|
||||
for ($i = 0; $i < $this->combatCount; ++$i)
|
||||
{
|
||||
$unitA->health = $unitA->health_max;
|
||||
$unitB->health = $unitB->health_max;
|
||||
$combat = new Daemon_Combat();
|
||||
$combat->addUnit('a', $unitA, true);
|
||||
$combat->addUnit('b', $unitB, false);
|
||||
$combat->execute(true);
|
||||
$deathA = ($unitA->health < 1);
|
||||
$deathB = ($unitB->health < 1);
|
||||
if ($deathA && $deathB)
|
||||
$this->doubleKOs += 1;
|
||||
elseif ($deathA)
|
||||
$this->winsB += 1;
|
||||
elseif ($deathB)
|
||||
$this->winsA += 1;
|
||||
else
|
||||
$this->draws += 1;
|
||||
$relHealthA = max(0.0, $unitA->health / $unitA->health_max);
|
||||
$relHealthB = max(0.0, $unitB->health / $unitB->health_max);
|
||||
$this->healthSumA += $relHealthA;
|
||||
$this->healthSumB += max(0.0, $relHealthB);
|
||||
$this->healthMinA = min($this->healthMinA, $relHealthA);
|
||||
$this->healthMinB = min($this->healthMinB, $relHealthB);
|
||||
$this->healthMaxA = max($this->healthMaxA, $relHealthA);
|
||||
$this->healthMaxB = max($this->healthMaxB, $relHealthB);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Scyzoryk_Controller_Page($cfg);
|
||||
$ctrl->execute();
|
98
2013/daemon/public/scyzoryk/character-edit.php
Normal file
98
2013/daemon/public/scyzoryk/character-edit.php
Normal file
|
@ -0,0 +1,98 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'../_init.php';
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_Controller_Page extends Daemon_Scyzoryk_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Postacie';
|
||||
protected $pageTemplatePath = 'scyzoryk/character-edit.xml';
|
||||
private $character;
|
||||
private $characterData;
|
||||
|
||||
|
||||
protected function prepareModel()
|
||||
{
|
||||
$this->character = new Daemon_DbObject_Character();
|
||||
$this->character->attachDbClient($this->dbClient);
|
||||
$this->character->get(array('character_id' => $this->editId));
|
||||
if (empty($this->character->character_id))
|
||||
{
|
||||
Daemon_MsgQueue::add('Wybrana postać nie istnieje.');
|
||||
Daemon::redirect($this->cfg->getUrl('scyzoryk/characters'));
|
||||
exit;
|
||||
}
|
||||
$this->characterData = $this->character->getCharacterData();
|
||||
}
|
||||
|
||||
|
||||
protected function prepareView()
|
||||
{
|
||||
$this->pageSubtitleDetails = $this->character ? $this->character->name : null;
|
||||
$this->view->character = $this->character;
|
||||
$this->view->characterData = $this->characterData;
|
||||
$this->view->genders = Daemon_Dictionary::$genders;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(is_null($this->character))
|
||||
return false;
|
||||
if(isset($_POST['save']))
|
||||
{
|
||||
$this->character->name = Daemon::getArrayValue($_POST, 'name');
|
||||
$this->character->gender = Daemon::getArrayValue($_POST, 'gender');
|
||||
$this->character->last_action = Daemon::getArrayValue($_POST, 'last_action');
|
||||
$this->character->clan_id = Daemon::getArrayValue($_POST, 'clan_id');
|
||||
$this->character->avatar_url = Daemon::getArrayValue($_POST, 'avatar_url');
|
||||
$this->character->quote = Daemon::getArrayValue($_POST, 'quote');
|
||||
$this->character->description = Daemon::getArrayValue($_POST, 'description');
|
||||
$this->character->put();
|
||||
return true;
|
||||
}
|
||||
if(isset($_POST['saveData']))
|
||||
{
|
||||
$this->characterData->location_id = Daemon::getArrayValue($_POST, 'location_id');
|
||||
$this->characterData->faction_id = Daemon::getArrayValue($_POST, 'faction_id');
|
||||
$this->characterData->faction_points = (int) Daemon::getArrayValue($_POST, 'faction_points');
|
||||
$this->characterData->rank_id = (int) Daemon::getArrayValue($_POST, 'rank_id');
|
||||
$this->characterData->turns = (int) Daemon::getArrayValue($_POST, 'turns');
|
||||
$this->characterData->gold_purse = (int) Daemon::getArrayValue($_POST, 'gold_purse');
|
||||
$this->characterData->gold_bank = (int) Daemon::getArrayValue($_POST, 'gold_bank');
|
||||
$this->characterData->level = (int) Daemon::getArrayValue($_POST, 'level');
|
||||
$this->characterData->xp_free = (int) Daemon::getArrayValue($_POST, 'xp_free');
|
||||
$this->characterData->health = (int) Daemon::getArrayValue($_POST, 'health');
|
||||
$this->characterData->health_max = (int) Daemon::getArrayValue($_POST, 'health_max');
|
||||
$this->characterData->mana = (int) Daemon::getArrayValue($_POST, 'mana');
|
||||
$this->characterData->mana_max = (int) Daemon::getArrayValue($_POST, 'mana_max');
|
||||
$this->characterData->a_str = (int) Daemon::getArrayValue($_POST, 'a_str');
|
||||
$this->characterData->a_dex = (int) Daemon::getArrayValue($_POST, 'a_dex');
|
||||
$this->characterData->a_vit = (int) Daemon::getArrayValue($_POST, 'a_vit');
|
||||
$this->characterData->a_pwr = (int) Daemon::getArrayValue($_POST, 'a_pwr');
|
||||
$this->characterData->a_wil = (int) Daemon::getArrayValue($_POST, 'a_wil');
|
||||
$this->characterData->s_pstr = (int) Daemon::getArrayValue($_POST, 's_pstr');
|
||||
$this->characterData->s_patk = (int) Daemon::getArrayValue($_POST, 's_patk');
|
||||
$this->characterData->s_pdef = (int) Daemon::getArrayValue($_POST, 's_pdef');
|
||||
$this->characterData->s_pres = (int) Daemon::getArrayValue($_POST, 's_pres');
|
||||
$this->characterData->s_preg = (int) Daemon::getArrayValue($_POST, 's_preg');
|
||||
$this->characterData->s_mstr = (int) Daemon::getArrayValue($_POST, 's_mstr');
|
||||
$this->characterData->s_matk = (int) Daemon::getArrayValue($_POST, 's_matk');
|
||||
$this->characterData->s_mdef = (int) Daemon::getArrayValue($_POST, 's_mdef');
|
||||
$this->characterData->s_mres = (int) Daemon::getArrayValue($_POST, 's_mres');
|
||||
$this->characterData->s_mreg = (int) Daemon::getArrayValue($_POST, 's_mreg');
|
||||
$this->characterData->sp_scout = (int) Daemon::getArrayValue($_POST, 'sp_scout');
|
||||
$this->characterData->sp_identify = (int) Daemon::getArrayValue($_POST, 'sp_identify');
|
||||
$this->characterData->sp_vchar = (int) Daemon::getArrayValue($_POST, 'sp_vchar');
|
||||
$this->characterData->sp_vmonster = (int) Daemon::getArrayValue($_POST, 'sp_vmonster');
|
||||
$this->characterData->sp_vitem = (int) Daemon::getArrayValue($_POST, 'sp_vitem');
|
||||
$this->characterData->put();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Scyzoryk_Controller_Page($cfg);
|
||||
$ctrl->execute();
|
30
2013/daemon/public/scyzoryk/characters.php
Normal file
30
2013/daemon/public/scyzoryk/characters.php
Normal file
|
@ -0,0 +1,30 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'../_init.php';
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_Controller_Page extends Daemon_Scyzoryk_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Postacie';
|
||||
protected $pageTemplatePath = 'scyzoryk/characters.xml';
|
||||
|
||||
|
||||
protected function prepareView()
|
||||
{
|
||||
$sql = "SELECT c.character_id, c.player_id, p.login AS player_login, c.name, c.last_action
|
||||
FROM characters c
|
||||
JOIN character_data cd USING(character_id)
|
||||
LEFT JOIN players p USING(player_id)
|
||||
ORDER BY c.character_id";
|
||||
$data = $this->dbClient->selectAll($sql);
|
||||
/*
|
||||
foreach ($data as &$row)
|
||||
$row['characters'] = explode("\n", $row['characters']);
|
||||
*/
|
||||
$this->view->rows = $data;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Scyzoryk_Controller_Page($cfg);
|
||||
$ctrl->execute();
|
51
2013/daemon/public/scyzoryk/combat-unit-edit.php
Normal file
51
2013/daemon/public/scyzoryk/combat-unit-edit.php
Normal file
|
@ -0,0 +1,51 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'../_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Page extends Daemon_Scyzoryk_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Jednostki bojowe';
|
||||
protected $pageTemplatePath = 'scyzoryk/combat-unit-edit.xml';
|
||||
private $unit;
|
||||
|
||||
|
||||
protected function prepareModel()
|
||||
{
|
||||
$this->unit = new Daemon_DbObject_CombatUnit();
|
||||
$this->unit->attachDbClient($this->dbClient);
|
||||
if($this->editId)
|
||||
$this->unit->get(array('combat_unit_id' => $this->editId));
|
||||
}
|
||||
|
||||
|
||||
protected function prepareView()
|
||||
{
|
||||
$this->pageSubtitleDetails = $this->unit ? $this->unit->name : null;
|
||||
$this->view->unit = $this->unit;
|
||||
$this->view->attackTypes = Daemon_Dictionary::$combatAttackTypes;
|
||||
$this->view->attackSpecials = Daemon_Dictionary::$combatAttackSpecials;
|
||||
$this->view->armorSpecials = Daemon_Dictionary::$combatArmorSpecials;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(isset($_POST['combat_unit_id']))
|
||||
{
|
||||
if(!$_POST['combat_unit_id'])
|
||||
{
|
||||
Daemon_MsgQueue::add('Uzupełnij ID.');
|
||||
return true;
|
||||
}
|
||||
$this->unit->import($_POST);
|
||||
$this->unit->put();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Page($cfg);
|
||||
$ctrl->execute();
|
61
2013/daemon/public/scyzoryk/combat-units.php
Normal file
61
2013/daemon/public/scyzoryk/combat-units.php
Normal file
|
@ -0,0 +1,61 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'../_init.php';
|
||||
|
||||
|
||||
class Daemon_Controller_Page extends Daemon_Scyzoryk_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Jednostki bojowe';
|
||||
protected $pageTemplatePath = 'scyzoryk/combat-units.xml';
|
||||
private $filter;
|
||||
|
||||
|
||||
protected function prepareModel()
|
||||
{
|
||||
$this->filter = new Daemon_Scyzoryk_Filter('combat-units');
|
||||
}
|
||||
|
||||
|
||||
protected function prepareView()
|
||||
{
|
||||
$this->view->filter = $this->filter;
|
||||
$units = array();
|
||||
foreach ($this->browser->getCombatUnits($this->filter) as $row)
|
||||
if (!$row['_character'])
|
||||
$units[] = $row;
|
||||
$this->view->units = $units;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
//add new row
|
||||
if(isset($_POST['newId'], $_POST['newName']) && $_POST['newId'])
|
||||
{
|
||||
$object = new Daemon_DbObject_CombatUnit();
|
||||
$object->attachDbClient($this->dbClient);
|
||||
$object->combat_unit_id = $_POST['newId'];
|
||||
$object->name = $_POST['newName'];
|
||||
$object->put();
|
||||
return true;
|
||||
}
|
||||
//delete rows
|
||||
if(isset($_POST['del']))
|
||||
{
|
||||
$this->editor->deleteCombatUnits($_POST['del']);
|
||||
return true;
|
||||
}
|
||||
//set filter
|
||||
if(isset($_POST['filter']) && is_array($_POST['filter']))
|
||||
{
|
||||
foreach($_POST['filter'] as $name => $value)
|
||||
$this->filter->$name = $value;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Controller_Page($cfg);
|
||||
$ctrl->execute();
|
51
2013/daemon/public/scyzoryk/config-generator.php
Normal file
51
2013/daemon/public/scyzoryk/config-generator.php
Normal file
|
@ -0,0 +1,51 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'../_init.php';
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_Controller_Config extends Daemon_Scyzoryk_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Ustawienia generatora';
|
||||
protected $pageTemplatePath = 'scyzoryk/config-generator.xml';
|
||||
private $dbCfg;
|
||||
private $itemTypes;
|
||||
|
||||
|
||||
protected function prepareModel()
|
||||
{
|
||||
$this->dbCfg = new Daemon_DbConfig($this->dbClient);
|
||||
$this->itemTypes = Daemon_Dictionary::$generatorItemTypes;
|
||||
}
|
||||
|
||||
|
||||
protected function prepareView()
|
||||
{
|
||||
$this->view->generatorBaseValue = $this->dbCfg->generatorBaseValue;
|
||||
$generatorOptions = array();
|
||||
foreach ($this->itemTypes as $type => $name)
|
||||
{
|
||||
$generatorOptions[$type] = array(
|
||||
'name' => $name,
|
||||
'weights' => $this->dbCfg->getGeneratorWeights("$type")
|
||||
);
|
||||
}
|
||||
$this->view->generatorOptions = $generatorOptions;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(isset($_POST['baseValue'], $_POST['weights']) && is_array($_POST['weights']))
|
||||
{
|
||||
$this->dbCfg->generatorBaseValue = max(1, (int) $_POST['baseValue']);
|
||||
foreach (array_keys($this->itemTypes) as $type)
|
||||
$this->dbCfg->setGeneratorWeights($type, $_POST['weights'][$type]);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Scyzoryk_Controller_Config($cfg);
|
||||
$ctrl->execute();
|
49
2013/daemon/public/scyzoryk/config.php
Normal file
49
2013/daemon/public/scyzoryk/config.php
Normal file
|
@ -0,0 +1,49 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
$cfg = require_once'../_init.php';
|
||||
|
||||
|
||||
class Daemon_Scyzoryk_Controller_Config extends Daemon_Scyzoryk_Controller
|
||||
{
|
||||
protected $pageSubtitle = 'Ustawienia';
|
||||
protected $pageTemplatePath = 'scyzoryk/config.xml';
|
||||
private $dbCfg;
|
||||
|
||||
|
||||
protected function prepareModel()
|
||||
{
|
||||
$this->dbCfg = new Daemon_DbConfig($this->dbClient);
|
||||
}
|
||||
|
||||
|
||||
protected function prepareView()
|
||||
{
|
||||
$this->view->cfg = $this->dbCfg;
|
||||
//healer
|
||||
$healer = explode(',', $this->dbCfg->healer);
|
||||
if(!isset($healer[0], $healer[1], $healer[2], $healer[3]))
|
||||
$healer = array(null, null, null, null);
|
||||
$this->view->healer = $healer;
|
||||
}
|
||||
|
||||
|
||||
protected function runCommands()
|
||||
{
|
||||
if(isset($_POST['cfg']) && is_array($_POST['cfg']))
|
||||
{
|
||||
$cfg = $_POST['cfg'];
|
||||
if(isset($_POST['healer']) && is_array($_POST['healer']))
|
||||
$cfg['healer'] = implode(',', $_POST['healer']);
|
||||
else $cfg['healer'] = '1,1,1,1';
|
||||
ksort($cfg);
|
||||
foreach($cfg as $name => $value)
|
||||
$this->dbCfg->$name = $value;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$ctrl = new Daemon_Scyzoryk_Controller_Config($cfg);
|
||||
$ctrl->execute();
|
20
2013/daemon/public/scyzoryk/cron-ui.php
Normal file
20
2013/daemon/public/scyzoryk/cron-ui.php
Normal file
|
@ -0,0 +1,20 @@
|
|||
<?php
|
||||
//@author Krzysztof Sikorski
|
||||
ini_set('display_errors', '1');
|
||||
$whitelist = array('127.0.0.1', '::1');
|
||||
if(isset($_POST['doit']) && in_array(getenv('REMOTE_ADDR'), $whitelist))
|
||||
{
|
||||
header('Content-Type:text/plain;charset=UTF-8');
|
||||
require implode(DIRECTORY_SEPARATOR, array(dirname(__FILE__), '..', '..', 'cron.php'));
|
||||
exit;
|
||||
}
|
||||
header('Content-Type:text/html;charset=UTF-8');
|
||||
?>
|
||||
<!doctype HTML>
|
||||
<html lang=pl>
|
||||
<meta charset="UTF-8">
|
||||
<title>Cron</title>
|
||||
<form action="" method=post>
|
||||
<p><input type=submit name=doit value=wykonaj></p>
|
||||
</form>
|
||||
</html>
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue