mirror of
https://github.com/openvk/openvk
synced 2024-12-23 09:01:15 +03:00
Users: Add the ability to convert votes into a rating for yourself or other users
Closes #345
This commit is contained in:
parent
b7559dcfe8
commit
13b614c377
9 changed files with 173 additions and 2 deletions
|
@ -1,6 +1,6 @@
|
||||||
<?php declare(strict_types=1);
|
<?php declare(strict_types=1);
|
||||||
namespace openvk\Web\Models\Entities\Notifications;
|
namespace openvk\Web\Models\Entities\Notifications;
|
||||||
use openvk\Web\Models\Entities\{User, Gift};
|
use openvk\Web\Models\Entities\User;
|
||||||
|
|
||||||
final class CoinsTransferNotification extends Notification
|
final class CoinsTransferNotification extends Notification
|
||||||
{
|
{
|
||||||
|
|
13
Web/Models/Entities/Notifications/RatingUpNotification.php
Normal file
13
Web/Models/Entities/Notifications/RatingUpNotification.php
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
<?php declare(strict_types=1);
|
||||||
|
namespace openvk\Web\Models\Entities\Notifications;
|
||||||
|
use openvk\Web\Models\Entities\User;
|
||||||
|
|
||||||
|
final class RatingUpNotification extends Notification
|
||||||
|
{
|
||||||
|
protected $actionCode = 9603;
|
||||||
|
|
||||||
|
function __construct(User $receiver, User $sender, int $value, string $message)
|
||||||
|
{
|
||||||
|
parent::__construct($receiver, $receiver, $sender, time(), $value . " " . $message);
|
||||||
|
}
|
||||||
|
}
|
|
@ -11,7 +11,7 @@ use openvk\Web\Models\Repositories\Notes;
|
||||||
use openvk\Web\Models\Repositories\Vouchers;
|
use openvk\Web\Models\Repositories\Vouchers;
|
||||||
use openvk\Web\Models\Exceptions\InvalidUserNameException;
|
use openvk\Web\Models\Exceptions\InvalidUserNameException;
|
||||||
use openvk\Web\Util\Validator;
|
use openvk\Web\Util\Validator;
|
||||||
use openvk\Web\Models\Entities\Notifications\CoinsTransferNotification;
|
use openvk\Web\Models\Entities\Notifications\{CoinsTransferNotification, RatingUpNotification};
|
||||||
use Chandler\Security\Authenticator;
|
use Chandler\Security\Authenticator;
|
||||||
use lfkeitel\phptotp\{Base32, Totp};
|
use lfkeitel\phptotp\{Base32, Totp};
|
||||||
use chillerlan\QRCode\{QRCode, QROptions};
|
use chillerlan\QRCode\{QRCode, QROptions};
|
||||||
|
@ -519,4 +519,44 @@ final class UserPresenter extends OpenVKPresenter
|
||||||
|
|
||||||
$this->flashFail("succ", tr("information_-1"), tr("points_transfer_successful", tr("points_amount", $value), $receiver->getURL(), htmlentities($receiver->getCanonicalName())));
|
$this->flashFail("succ", tr("information_-1"), tr("points_transfer_successful", tr("points_amount", $value), $receiver->getURL(), htmlentities($receiver->getCanonicalName())));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function renderIncreaseRating(): void
|
||||||
|
{
|
||||||
|
$this->assertUserLoggedIn();
|
||||||
|
$this->willExecuteWriteAction();
|
||||||
|
|
||||||
|
if(!OPENVK_ROOT_CONF["openvk"]["preferences"]["commerce"])
|
||||||
|
$this->flashFail("err", tr("error"), tr("feature_disabled"));
|
||||||
|
|
||||||
|
$receiverAddress = $this->postParam("receiver");
|
||||||
|
$value = (int) $this->postParam("value");
|
||||||
|
$message = $this->postParam("message");
|
||||||
|
|
||||||
|
if(!$receiverAddress || !$value)
|
||||||
|
$this->flashFail("err", tr("failed_to_increase_rating"), tr("not_all_information_has_been_entered"));
|
||||||
|
|
||||||
|
if($value < 0)
|
||||||
|
$this->flashFail("err", tr("failed_to_increase_rating"), tr("negative_rating_value"));
|
||||||
|
|
||||||
|
if(iconv_strlen($message) > 255)
|
||||||
|
$this->flashFail("err", tr("failed_to_increase_rating"), tr("message_is_too_long"));
|
||||||
|
|
||||||
|
$receiver = $this->users->getByAddress($receiverAddress);
|
||||||
|
if(!$receiver)
|
||||||
|
$this->flashFail("err", tr("failed_to_increase_rating"), tr("receiver_not_found"));
|
||||||
|
|
||||||
|
if($this->user->identity->getCoins() < $value)
|
||||||
|
$this->flashFail("err", tr("failed_to_increase_rating"), tr("you_dont_have_enough_points"));
|
||||||
|
|
||||||
|
$this->user->identity->setCoins($this->user->identity->getCoins() - $value);
|
||||||
|
$this->user->identity->save();
|
||||||
|
|
||||||
|
$receiver->setRating($receiver->getRating() + $value);
|
||||||
|
$receiver->save();
|
||||||
|
|
||||||
|
if($this->user->id !== $receiver->getId())
|
||||||
|
(new RatingUpNotification($receiver, $this->user->identity, $value, $message))->emit();
|
||||||
|
|
||||||
|
$this->flashFail("succ", tr("information_-1"), tr("rating_increase_successful", $receiver->getURL(), htmlentities($receiver->getCanonicalName()), $value));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -72,6 +72,9 @@
|
||||||
<div id="profile_link" style="width: 194px;">
|
<div id="profile_link" style="width: 194px;">
|
||||||
<a href="/edit" class="link">{_"edit_page"}</a>
|
<a href="/edit" class="link">{_"edit_page"}</a>
|
||||||
</div>
|
</div>
|
||||||
|
<div n:if="OPENVK_ROOT_CONF['openvk']['preferences']['commerce']" id="profile_link" style="width: 194px;">
|
||||||
|
<a onClick="showIncreaseRatingDialog({$thisUser->getCoins()}, {ltrim($thisUser->getUrl(), '/')}, {$csrfToken})" class="link">{_increase_rating}</a>
|
||||||
|
</div>
|
||||||
{else}
|
{else}
|
||||||
{if $thisUser->getChandlerUser()->can("substitute")->model('openvk\Web\Models\Entities\User')->whichBelongsTo(0)}
|
{if $thisUser->getChandlerUser()->can("substitute")->model('openvk\Web\Models\Entities\User')->whichBelongsTo(0)}
|
||||||
<a href="/setSID/{$user->getChandlerUser()->getId()}?hash={rawurlencode($csrfToken)}" class="profile_link">
|
<a href="/setSID/{$user->getChandlerUser()->getId()}?hash={rawurlencode($csrfToken)}" class="profile_link">
|
||||||
|
|
|
@ -0,0 +1,8 @@
|
||||||
|
{var sender = $notification->getModel(1)}
|
||||||
|
{var value = (int) explode(" ", $notification->getData(), 2)[0]}
|
||||||
|
{var message = explode(" ", $notification->getData(), 2)[1]}
|
||||||
|
|
||||||
|
<a href="{$sender->getURL()}"><b>{$sender->getCanonicalName()}</b></a> {_increased_your_rating_by} {$value}%.
|
||||||
|
{if !empty($message)}
|
||||||
|
{_message}: "{$message}".
|
||||||
|
{/if}
|
|
@ -73,6 +73,8 @@ routes:
|
||||||
handler: "User->disableTwoFactorAuth"
|
handler: "User->disableTwoFactorAuth"
|
||||||
- url: "/coins_transfer"
|
- url: "/coins_transfer"
|
||||||
handler: "User->coinsTransfer"
|
handler: "User->coinsTransfer"
|
||||||
|
- url: "/increase_social_credits"
|
||||||
|
handler: "User->increaseRating"
|
||||||
- url: "/id{num}"
|
- url: "/id{num}"
|
||||||
handler: "User->view"
|
handler: "User->view"
|
||||||
- url: "/friends{num}"
|
- url: "/friends{num}"
|
||||||
|
|
|
@ -289,3 +289,78 @@ function supportFastAnswerDialogOnClick(answer) {
|
||||||
answerInput.value = answer;
|
answerInput.value = answer;
|
||||||
answerInput.focus();
|
answerInput.focus();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function ovk_proc_strtr(string, length = 0) {
|
||||||
|
const newString = string.substring(0, length);
|
||||||
|
return newString + (string !== newString ? "…" : "");
|
||||||
|
}
|
||||||
|
|
||||||
|
function showIncreaseRatingDialog(coinsCount, userUrl, hash) {
|
||||||
|
MessageBox(tr("increase_rating"), `
|
||||||
|
<div class="messagebox-content-header">
|
||||||
|
${tr("you_have_unused_votes", coinsCount)} <br />
|
||||||
|
<a href="/settings?act=finance.top-up">${tr("apply_voucher")} »</a>
|
||||||
|
</div>
|
||||||
|
<form action="/increase_social_credits" method="post" id="increase_rating_form" style="margin-top: 30px">
|
||||||
|
<table cellspacing="7" cellpadding="0" border="0" align="center">
|
||||||
|
<tbody>
|
||||||
|
<tr>
|
||||||
|
<td width="120" valign="top">
|
||||||
|
<span class="nobold">${tr("to_whom")}:</span>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<input type="text" name="receiver" style="width: 100%;" value="${userUrl}" />
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td width="120" valign="top">
|
||||||
|
<span class="nobold">${tr("increase_by")}:</span>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<input id="value_input" type="text" name="value" style="width: 100%;" />
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td width="120" valign="top">
|
||||||
|
<span class="nobold">${tr("message")}:</span>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<textarea name="message" style="width: 100%;"></textarea>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td colspan="2">
|
||||||
|
<div class="menu_divider"></div>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td width="120" valign="top">
|
||||||
|
<span class="nobold">${tr("price")}:</span>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<span id="rating_price">${tr("points_amount", 0)}</span> <small class="nobold" style="float: right;">(1% = ${tr("points_amount_one", 1)})</small>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<input type="hidden" name="hash" value="${hash}" />
|
||||||
|
</form>
|
||||||
|
`, [tr("increase_rating_button"), tr("cancel")], [
|
||||||
|
() => {
|
||||||
|
document.querySelector("#increase_rating_form").submit();
|
||||||
|
},
|
||||||
|
Function.noop
|
||||||
|
]);
|
||||||
|
|
||||||
|
document.querySelector("#value_input").oninput = function () {
|
||||||
|
let value = Number(this.value);
|
||||||
|
value = isNaN(value) ? "?" : ovk_proc_strtr(String(value), 7);
|
||||||
|
if(!value.endsWith("…") && value != "?")
|
||||||
|
value = Number(value);
|
||||||
|
|
||||||
|
if(typeof value === "number")
|
||||||
|
document.querySelector("#rating_price").innerHTML = tr("points_amount", value);
|
||||||
|
else
|
||||||
|
document.querySelector("#rating_price").innerHTML = value + " " + tr("points_amount_other").replace("$1 ", "");
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
|
@ -583,6 +583,21 @@
|
||||||
"receiver_not_found" = "The receiver was not found.";
|
"receiver_not_found" = "The receiver was not found.";
|
||||||
"you_dont_have_enough_points" = "You don't have enough votes.";
|
"you_dont_have_enough_points" = "You don't have enough votes.";
|
||||||
|
|
||||||
|
"increase_rating" = "Increase rating";
|
||||||
|
"increase_rating_button" = "Increase";
|
||||||
|
"to_whom" = "To whom";
|
||||||
|
"increase_by" = "Increase by";
|
||||||
|
"price" = "Price";
|
||||||
|
|
||||||
|
"you_have_unused_votes" = "You have $1 unused votes on your balance.";
|
||||||
|
"apply_voucher" = "Apply voucher";
|
||||||
|
|
||||||
|
"failed_to_increase_rating" = "Failed to increase rating";
|
||||||
|
"rating_increase_successful" = "You have successfully increased rating of <b><a href=\"$1\">$2</a></b> by <b>$3%</b>.";
|
||||||
|
"negative_rating_value" = "We cannot steal rating from another person, sorry.";
|
||||||
|
|
||||||
|
"increased_your_rating_by" = "increased your rating by";
|
||||||
|
|
||||||
/* Gifts */
|
/* Gifts */
|
||||||
|
|
||||||
"gift" = "Gift";
|
"gift" = "Gift";
|
||||||
|
|
|
@ -609,6 +609,21 @@
|
||||||
"receiver_not_found" = "Получатель не найден.";
|
"receiver_not_found" = "Получатель не найден.";
|
||||||
"you_dont_have_enough_points" = "У вас недостаточно голосов.";
|
"you_dont_have_enough_points" = "У вас недостаточно голосов.";
|
||||||
|
|
||||||
|
"increase_rating" = "Повысить рейтинг";
|
||||||
|
"increase_rating_button" = "Повысить";
|
||||||
|
"to_whom" = "Кому";
|
||||||
|
"increase_by" = "Повысить на";
|
||||||
|
"price" = "Стоимость";
|
||||||
|
|
||||||
|
"you_have_unused_votes" = "У Вас $1 неиспользованных голоса на балансе.";
|
||||||
|
"apply_voucher" = "Применить ваучер";
|
||||||
|
|
||||||
|
"failed_to_increase_rating" = "Не удалось повысить рейтинг";
|
||||||
|
"rating_increase_successful" = "Вы успешно повысыли рейтинг <b><a href=\"$1\">$2</a></b> на <b>$3%</b>.";
|
||||||
|
"negative_rating_value" = "Мы не можем украсть рейтинг у другого человека, извините.";
|
||||||
|
|
||||||
|
"increased_your_rating_by" = "повысил ваш рейтинг на";
|
||||||
|
|
||||||
/* Gifts */
|
/* Gifts */
|
||||||
|
|
||||||
"gift" = "Подарок";
|
"gift" = "Подарок";
|
||||||
|
|
Loading…
Reference in a new issue