battles/classes/Battles/ShopItem.php

215 lines
9.5 KiB
PHP
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<?php
namespace Battles;
use Battles\Database\DBPDO;
use Exceptions\GameException;
class ShopItem extends Item
{
private const NO_ITEMS_IN_STOCK = "Товара нет в наличии!";
private const NO_MONEY = "У вас нет денег!";
private const BUTTON = [
'setmarket' => 'Сдать в магазин',
'unsetmarket' => 'Снять с продажи',
'buymarket' => 'Совершить обмен',
'sellshop' => 'Продать',
'buyshop' => 'Купить',
];
private const BUY_QUERY = 'insert into inventory (owner_id, name, item_type, durability,
need_strength, need_dexterity, need_intuition, need_endurance, need_intelligence, need_wisdom,
add_strength, add_dexterity, add_intuition, add_endurance, add_intelligence, add_wisdom,
add_accuracy, add_evasion, add_criticals, add_min_physical_damage, add_max_physical_damage,
image, weight, price)
select
?,
ifnull(name,\'Неизвестный предмет\'),
ifnull(item_type,0),
ifnull(durability, 1),
ifnull(need_strength, 0),
ifnull(need_dexterity, 0),
ifnull(need_intuition, 0),
ifnull(need_endurance, 0),
ifnull(need_intelligence, 0),
ifnull(need_wisdom, 0),
ifnull(add_strength, 0),
ifnull(add_dexterity, 0),
ifnull(add_intuition, 0),
ifnull(add_endurance, 0),
ifnull(add_intelligence, 0),
ifnull(add_wisdom, 0),
ifnull(add_accuracy, 0),
ifnull(add_evasion, 0),
ifnull(add_criticals, 0),
ifnull(add_min_physical_damage, 0),
ifnull(add_max_physical_damage, 0),
ifnull(image, \'noitem.png\'),
ifnull(weight, 1),
?
from items where id = ?';
// Тип операции в магазине. Для отображения разных блоков в разных случаях.
private $optype;
private ?int $shop_item_quantity;
private ?int $bank_price;
private ?int $price;
public function __construct($row, $operationType = null)
{
parent::__construct($row);
if ($operationType) {
$this->optype = $operationType;
}
$this->price = $row->price ?? null;
$this->shop_item_quantity = $row->shop_item_quantity ?? null;
$this->bank_price = $row->bank_price ?? null;
$this->item_id = $row->item_id ?? $row->id;
}
public function printInfo()
{
$this->printAllInfo();
if ($this->optype === 'buyshop') {
if ($this->bank_price) {
echo "<div>Цена: $this->bank_price банкнот.</div>";
}
if ($this->shop_item_quantity > 0 && $this->shop_item_quantity < 20) {
echo "<div style='margin-top: 9px; font-style: italic;'>На складе осталось $this->shop_item_quantity единиц товара!</div>";
}
}
if ($this->optype === 'sellshop') {
if ($this->getSellPriceMean() < 50) {
$goods = 'этот хлам';
} elseif ($this->getSellPriceMean() < 100) {
$goods = 'этот посредственный товар';
} elseif ($this->getSellPriceMean() < 500) {
$goods = 'этот неплохой предмет';
} elseif ($this->getSellPriceMean() < 1000) {
$goods = 'эту отличную штуку';
} else {
$goods = 'это превосходное изделие';
}
echo "<div style='margin-top: 9px; font-style: italic;'>В среднем за $goods можно выручить <span class='success'>{$this->getSellPriceMean()}</span> кр.</div>";
}
}
public function printImage(): string
{
if (!$this->image) {
$this->image = 'noitem.png';
}
return "<img src='/i/sh/$this->image' class='item-wrap-normal' alt=''>";
}
public static function buyItem($id, User $buyer): string
{
$db = new DBPDO();
$check = $db->ofetch("select * from trade_offers where shop_item_id = ?", $id);
$itemPrice = $check->bank_price ?? 0;
if (empty($check->shop_item_quantity) || empty($check->shop_item_id)) {
return self::NO_ITEMS_IN_STOCK;
}
// TODO БАРТЕР!
if (isset($check->barter_item_list_json)) {
echo "Работаем по бартеру!";
}
$db->execute(self::BUY_QUERY, [$buyer->getId(), $itemPrice, $check->shop_item_id]);
$item = $db->ofetch("select item_id, name, price from inventory where item_id = ?", $db->lastInsertId());
if (empty($item->item_id) || empty($item->name) || empty($item->price)) {
return 'Запрос в базу не прошёл.';
} else {
$boughtItemId = $item->item_id;
$boughtItemName = $item->name;
$boughtItemPrice = $item->price;
if ($item->price > 0) {
try {
$bank = new Bank($buyer->getId());
$bank->withdrawMoney($item->price);
} catch (GameException $e) {
echo 'Банковская ошибка!';
return self::NO_MONEY;
}
}
}
if ($check->shop_item_quantity != -1) {
$db->execute("update trade_offers set shop_item_quantity = shop_item_quantity -1 where shop_item_id = ?", $check->shop_item_id);
}
$deloText = $buyer->getLogin() . " купил товар «" . $boughtItemName . "» id:(" . $boughtItemId . ") в магазине за " . $boughtItemPrice . " банкнот.";
GameLogs::addUserLog($buyer->getId(), $deloText);
return "Предмет " . $boughtItemName . " куплен за " . $boughtItemPrice . " банкнот.";
}
//TODO не пишутся логи продажи!
/** TODO
* Notice: Undefined index: shopsell in /volume2/web/battles/classes/Battles/Bank.php on line 199 Call Stack: 0.0003 430192
* 1. {main}() /volume2/web/battles/shop.php:0 0.0051 966928
* 2. Battles\ShopItem::sellItem() /volume2/web/battles/shop.php:21 0.1067 998536
* 3. Battles\Bank::setBankMoney() /volume2/web/battles/classes/Battles/ShopItem.php:162
* Не отработал запрос в БД в файле /volume2/web/battles/classes/Battles/GameLogs.php(20)
*/
public static function sellItem($id, User $seller, $bankTrade = 0): string
{
$db = new DBPDO();
$item = $db->ofetch('select * from inventory where item_id = ?', $id);
$sellingItemName = $item->name;
// Продажа за цену от нуля до половины стоимости.
$sellingPrice = mt_rand(0, $item->price / 2);
$db->execute('delete from inventory where item_id = ?', $id);
if ($bankTrade) {
$bank = new Bank($seller->getId());
$bank->setMoney($bank->getMoney() + $sellingPrice);
Bank::setBankMoney($bank->getMoney(), $seller->getId(), 'shopsell');
} else {
$db->execute('update users set money = money - ? where id = ?', [$sellingPrice, $_SESSION['uid']]);
}
$deloText = "{$seller->getLogin()} продал товар «{$sellingItemName}» id:($id) в магазине за $sellingPrice кр.";
GameLogs::addUserLog($seller->getId(), $deloText);
if ($sellingPrice == 0) {
$status = "После длительных и изнурительных торгов вы плюнули на всё и просто подарили ваш «{$sellingItemName}» торговцу.";
} else {
$status = "Вы продали «{$sellingItemName}» за $sellingPrice кр.";
}
return $status;
}
/** Подчсчёт средней суммы продажи.
* @return int
*/
private function getSellPriceMean(): ?int
{
if ($this->price) {
$arr = range(0, $this->price / 2);
return array_sum($arr) / sizeof($arr);
}
return null;
}
/**
* Для кнопок управления под картинкой предмета в зависимости от ситуации.
*/
public function printControls()
{
if (in_array($this->optype, ['setmarket', 'unsetmarket', 'buymarket', 'sellshop', 'buyshop',])) {
$str = $this->optype == 'setmarket' ? '<input placeholder=" ' . $this->price . ' " name="cost">' : '';
$button_name = self::BUTTON[$this->optype];
echo <<<FORM
<form method="post">$str
<input type="hidden" name="itemId" value="$this->item_id">
<br><input type="submit" name="$this->optype" value="$button_name">
</form>
FORM;
}
}
/**
* @return mixed
*/
public function getItemType()
{
return $this->item_type;
}
}