Implementadas Varias funciones de Pago de Stripe para Opciones Personajes, La Tienda Todavia no esta implementada del todo (EXPERIMENTAL)

This commit is contained in:
adevopg
2024-12-01 20:35:40 +01:00
parent 07b1281d61
commit 9c74006148
78 changed files with 2036 additions and 25 deletions
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
+33 -1
View File
@@ -3,7 +3,7 @@ from django.contrib import admin
from django import forms
from .models import (
Noticia, ClienteCategoria, SistemaOperativo, ServerSelection,
RecruitAFriend, DownloadClientPage, ContentCreator, RecruitReward, GuildRenameSettings, VoteSite
RecruitAFriend, DownloadClientPage, ContentCreator, RecruitReward, GuildRenameSettings, VoteSite, RenamePrice, CustomizePrice, ChangeRacePrice, ChangeFactionPrice, LevelUpPrice, GoldPrice, TransferPrice
)
from django.db import connections
import logging
@@ -12,6 +12,25 @@ from django_ckeditor_5.widgets import CKEditor5Widget
logger = logging.getLogger(__name__)
@admin.register(ChangeFactionPrice)
class ChangeFactionPriceAdmin(admin.ModelAdmin):
list_display = ('price',)
@admin.register(GoldPrice)
class GoldPriceAdmin(admin.ModelAdmin):
list_display = ('gold_amount', 'price')
ordering = ('gold_amount',)
@admin.register(TransferPrice)
class TransferPriceAdmin(admin.ModelAdmin):
list_display = ('price',)
@admin.register(LevelUpPrice)
class LevelUpPriceAdmin(admin.ModelAdmin):
list_display = ('price',)
# Formulario para el modelo Noticia
class NoticiaAdminForm(forms.ModelForm):
class Meta:
@@ -21,6 +40,19 @@ class NoticiaAdminForm(forms.ModelForm):
'contenido': CKEditor5Widget(config_name='default'),
}
@admin.register(RenamePrice)
class RenamePriceAdmin(admin.ModelAdmin):
list_display = ("price",)
@admin.register(CustomizePrice)
class CustomizePriceAdmin(admin.ModelAdmin):
list_display = ("price",)
@admin.register(ChangeRacePrice)
class ChangeRacePriceAdmin(admin.ModelAdmin):
list_display = ('price',)
@admin.register(Noticia)
class NoticiaAdmin(admin.ModelAdmin):
form = NoticiaAdminForm
+83
View File
@@ -21,6 +21,89 @@ class UnstuckHistory(models.Model):
character_name = models.CharField(max_length=50)
used_at = models.DateTimeField()
class ReviveHistory(models.Model):
character_name = models.CharField(max_length=50)
used_at = models.DateTimeField()
def __str__(self):
return f"{self.character_name} - {self.used_at}"
class ChangeFactionPrice(models.Model):
price = models.DecimalField(max_digits=6, decimal_places=2, default=10.00)
def __str__(self):
return f"Precio para cambiar facción: {self.price} EUR"
class LevelUpPrice(models.Model):
price = models.DecimalField(max_digits=10, decimal_places=2, default=10.00)
def __str__(self):
return f"Subir a nivel 80: {self.price} EUR"
class GoldPrice(models.Model):
gold_amount = models.IntegerField() # Cantidad de oro
price = models.DecimalField(max_digits=10, decimal_places=2) # Precio en EUR
def __str__(self):
return f"{self.gold_amount} oro - {self.price} EUR"
class TransferPrice(models.Model):
price = models.DecimalField(max_digits=5, decimal_places=2)
def __str__(self):
return f"Precio de transferencia: {self.price} EUR"
class StoreCategory(models.Model):
name = models.CharField(max_length=100)
parent_category = models.ForeignKey('self', null=True, blank=True, on_delete=models.CASCADE)
def __str__(self):
return self.name
class StoreItem(models.Model):
name = models.CharField(max_length=200)
item_id = models.IntegerField()
category = models.ForeignKey(StoreCategory, on_delete=models.CASCADE)
image_url = models.URLField()
price = models.DecimalField(max_digits=6, decimal_places=2) # Precio en euros
def __str__(self):
return self.name
class Cart(models.Model):
username = models.CharField(max_length=150) # Para almacenar el nombre de usuario
item = models.ForeignKey(StoreItem, on_delete=models.CASCADE)
added_at = models.DateTimeField(auto_now_add=True)
def total_price(self):
return self.item.price
class RenamePrice(models.Model):
price = models.DecimalField(max_digits=5, decimal_places=2, default=2.00)
def __str__(self):
return f"{self.price} EUR"
class CustomizePrice(models.Model):
price = models.DecimalField(max_digits=5, decimal_places=2, default=1.00)
def __str__(self):
return f"{self.price} EUR"
class ChangeRacePrice(models.Model):
price = models.DecimalField(max_digits=5, decimal_places=2)
def __str__(self):
return f"Cambiar raza: {self.price} EUR"
class ClienteCategoria(models.Model):
nombre = models.CharField(max_length=100)
+24
View File
@@ -0,0 +1,24 @@
import stripe
from django.conf import settings
stripe.api_key = settings.STRIPE_SECRET_KEY
def create_checkout_session(amount, currency="eur", success_url=None, cancel_url=None):
try:
session = stripe.checkout.Session.create(
payment_method_types=["card"],
line_items=[{
"price_data": {
"currency": currency,
"product_data": {"name": "Renombrar personaje"},
"unit_amount": int(amount * 100), # Convertir euros a centavos
},
"quantity": 1,
}],
mode="payment",
success_url=success_url,
cancel_url=cancel_url,
)
return {"success": True, "session_id": session.id}
except Exception as e:
return {"success": False, "error": str(e)}
@@ -0,0 +1,45 @@
if (window.history.replaceState) {
window.history.replaceState(null, null, window.location.href);
};
$(function(){
$('.change-faction-button').on('click', function(e) {
e.preventDefault();
$("#change-faction-response").empty();
var button = $(this);
var buttonoriginal = button.html();
var data = $("#nw-change-faction-form").serialize();
var conf = confirm("¿Estás seguro de cambiar de facción al personaje seleccionado?");
if (conf === true) {
changeButton(button, 'Procesando pago...');
$.ajax({
type: 'POST',
url: '', // URL actual
data: data,
dataType: 'json',
success: function(response) {
if (response.success) {
var stripe = Stripe(response.stripe_public_key);
stripe.redirectToCheckout({ sessionId: response.session_id }).then(function(result) {
if (result.error) {
$("#change-faction-response").append('<span class="red-form-response">' + result.error.message + '</span>').hide().slideDown();
restoreButton(button, buttonoriginal);
}
});
} else {
$("#change-faction-response").append(response.message).hide().slideDown();
restoreButton(button, buttonoriginal);
}
},
error: function() {
$("#change-faction-response").append('<span class="red-form-response">Error inesperado. Por favor, intente más tarde.</span>').hide().slideDown();
restoreButton(button, buttonoriginal);
}
});
}
});
});
@@ -0,0 +1,73 @@
if (window.history.replaceState) {
window.history.replaceState(null, null, window.location.href);
}
function doRefresh() {
$("#nw-change-race-form").load(document.URL + " #nw-change-race-form>*", function () {
$.getScript('nw-js-handlers/change_race_response.js');
});
}
$(function () {
$('select').on('change', function () {
var select = $(this);
select.css('color', select.children('option:selected').css('color'));
});
});
$(function () {
$('.change-race-button').on('click', function (e) {
e.preventDefault();
e.stopPropagation();
$("#change-race-response").empty();
var button = $(this);
var buttonoriginal = button.html();
var data = $("#nw-change-race-form").serialize();
var conf = confirm("¿Estás seguro de cambiar de raza al personaje seleccionado?");
if (conf === true) {
changeButton(button, 'Procesando pago...');
$.ajax({
type: 'POST',
url: '', // La URL para manejar la solicitud POST
data: data,
dataType: 'json',
success: function (response) {
if (response.success) {
// Verificar si Stripe.js está disponible
if (typeof Stripe === 'undefined') {
console.error("Stripe.js no está cargado.");
$("#change-race-response").append('<span class="red-form-response">Error al cargar Stripe. Intente nuevamente más tarde.</span>').hide().slideDown();
restoreButton(button, buttonoriginal);
return;
}
// Inicializar Stripe con la clave pública
var stripe = Stripe(response.stripe_public_key);
// Redirigir al checkout de Stripe
stripe.redirectToCheckout({
sessionId: response.session_id
}).then(function (result) {
if (result.error) {
$("#change-race-response").append('<span class="red-form-response">' + result.error.message + '</span>').hide().slideDown();
restoreButton(button, buttonoriginal);
}
});
} else {
$("#change-race-response").append(response.message).hide().slideDown();
restoreButton(button, buttonoriginal);
}
},
error: function () {
setTimeout(function () {
alert("Algo ha salido mal. Por favor intente más tarde");
window.location.reload();
}, 2000);
}
});
}
});
});
@@ -0,0 +1,52 @@
if (window.history.replaceState) {
window.history.replaceState(null, null, window.location.href);
}
$(function(){
$('.customize-button').on('click', function(e) {
e.preventDefault();
$("#customize-response").empty();
var button = $(this);
var buttonoriginal = button.html();
var data = $("#nw-customize-form").serialize();
var conf = confirm("¿Estás seguro de personalizar al personaje seleccionado?");
if (conf === true) {
button.html("Procesando pago...");
button.prop("disabled", true);
$.ajax({
type: 'POST',
url: '', // Endpoint para manejar el POST
data: data,
dataType: 'json',
success: function(response) {
if (response.success) {
var stripe = Stripe(response.stripe_public_key);
stripe.redirectToCheckout({
sessionId: response.session_id
}).then(function(result) {
if (result.error) {
$("#customize-response").html('<span class="red-form-response">' + result.error.message + '</span>');
button.html(buttonoriginal);
button.prop("disabled", false);
}
});
} else {
$("#customize-response").html(response.message);
button.html(buttonoriginal);
button.prop("disabled", false);
}
},
error: function() {
$("#customize-response").html('<span class="red-form-response">Algo salió mal. Intenta de nuevo.</span>');
button.html(buttonoriginal);
button.prop("disabled", false);
}
});
}
});
});
@@ -0,0 +1,35 @@
$(function(){
$('.gold-button').on('click', function(e) {
e.preventDefault();
$("#gold-response").empty();
var button = $(this);
var originalText = button.html();
var data = $("#uw-gold-form").serialize();
button.html('Procesando pago...');
button.prop('disabled', true);
$.ajax({
type: 'POST',
url: '',
data: data,
dataType: 'json',
success: function(response) {
if (response.success) {
var stripe = Stripe(response.stripe_public_key);
stripe.redirectToCheckout({ sessionId: response.session_id });
} else {
$("#gold-response").append(response.message).hide().slideDown();
button.html(originalText);
button.prop('disabled', false);
}
},
error: function() {
$("#gold-response").append('<span class="red-form-response">Error inesperado. Por favor, intente más tarde.</span>').hide().slideDown();
button.html(originalText);
button.prop('disabled', false);
}
});
});
});
@@ -0,0 +1,47 @@
if (window.history.replaceState) {
window.history.replaceState(null, null, window.location.href);
}
$(function() {
$('.level-up-button').on('click', function(e) {
e.preventDefault();
$("#levelup-response").empty();
var button = $(this);
var buttonoriginal = button.html();
var data = $("#nw-levelup-form").serialize();
var conf = confirm("¿Estás seguro de subir al nivel 80 al personaje seleccionado?");
if (conf === true) {
changeButton(button, 'Procesando pago...');
$.ajax({
type: 'POST',
url: '',
data: data,
dataType: 'json',
success: function(response) {
if (response.success) {
var stripe = Stripe(response.stripe_public_key);
stripe.redirectToCheckout({
sessionId: response.session_id
}).then(function(result) {
if (result.error) {
$("#levelup-response").append('<span class="red-form-response">' + result.error.message + '</span>').hide().slideDown();
restoreButton(button, buttonoriginal);
}
});
} else {
$("#levelup-response").append(response.message).hide().slideDown();
restoreButton(button, buttonoriginal);
}
},
error: function() {
$("#levelup-response").append('<span class="red-form-response">Error inesperado. Por favor intente más tarde.</span>').hide().slideDown();
restoreButton(button, buttonoriginal);
}
});
}
});
});
@@ -45,7 +45,7 @@ $(function() {
// Serializar datos para el envío
const bValue = button.data('id');
let data = { login: bValue };
data = $("#uw-login-form").serialize() + '&' + $.param(data);
data = $("#nw-login-form").serialize() + '&' + $.param(data);
$.ajax({
type: 'POST',
@@ -1,6 +1,6 @@
$(function() {
// Manejar el envío del formulario de creación de cuenta
$('#uw-create-form').on('submit', function(e) {
$('#nw-create-form').on('submit', function(e) {
e.preventDefault();
const data = $(this).serialize();
const createResponse = $("#create-response");
@@ -0,0 +1,75 @@
if (window.history.replaceState) {
window.history.replaceState(null, null, window.location.href);
}
$(document).ready(function () {
// Mostrar mensaje de cancelación si está presente en el backend
const cancelMessage = $("#rename-response").data("cancel-message");
if (cancelMessage) {
$("#rename-response").html(cancelMessage).hide().slideDown();
}
// Manejar clics en el botón de renombrar
$('.rename-button').on('click', function (e) {
e.preventDefault();
$("#rename-response").empty();
const button = $(this);
const originalText = button.html();
const data = $("#nw-rename-form").serialize();
// Confirmar antes de proceder con el pago
const conf = confirm("¿Estás seguro de renombrar al personaje seleccionado?");
if (!conf) return;
// Cambiar texto del botón mientras procesa
changeButton(button, 'Procesando pago...');
$.ajax({
type: 'POST',
url: '', // URL para manejar el POST
data: data,
dataType: 'json',
success: function (response) {
if (response.success) {
// Verificar que Stripe está cargado
if (typeof Stripe === 'undefined') {
console.error("Stripe.js no está cargado.");
$("#rename-response").append('<span class="red-form-response">Error al cargar Stripe. Intente nuevamente más tarde.</span>').hide().slideDown();
restoreButton(button, originalText);
return;
}
// Redirigir a Stripe Checkout
const stripe = Stripe(response.stripe_public_key);
stripe.redirectToCheckout({ sessionId: response.session_id }).then(function (result) {
if (result.error) {
$("#rename-response").append('<span class="red-form-response">' + result.error.message + '</span>').hide().slideDown();
restoreButton(button, originalText);
}
});
} else {
// Mostrar mensaje de error del backend
$("#rename-response").append(response.message).hide().slideDown();
restoreButton(button, originalText);
}
},
error: function () {
$("#rename-response").append('<span class="red-form-response">Error inesperado. Por favor, intente más tarde.</span>').hide().slideDown();
restoreButton(button, originalText);
}
});
});
});
// Función para cambiar el texto del botón y desactivarlo
function changeButton(button, text) {
button.html(text);
button.prop("disabled", true);
}
// Función para restaurar el texto y habilitar el botón
function restoreButton(button, originalText) {
button.html(originalText);
button.prop("disabled", false);
}
@@ -0,0 +1,37 @@
$(document).ready(function() {
$('.revive-button').on('click', function(e) {
e.preventDefault();
$("#revive-response").empty();
var button = $(this);
var originalText = button.html();
var data = $("#nw-revive-form").serialize();
button.html("Reviviendo...");
button.prop("disabled", true);
$.ajax({
type: 'POST',
url: '',
data: data,
dataType: 'json',
success: function(response) {
$("#revive-response").html(response.message).hide().slideDown();
if (response.success) {
button.html("Revivido");
setTimeout(function() {
location.reload(); // Refrescar para actualizar el formulario
}, 5000);
} else {
button.html(originalText);
button.prop("disabled", false);
}
},
error: function(xhr, status, error) {
$("#revive-response").html('<span class="red-form-response">Algo salió mal. Intente nuevamente.</span>');
button.html(originalText);
button.prop("disabled", false);
}
});
});
});
@@ -4,7 +4,7 @@ $(function() {
var button = $(this);
var originalText = button.html();
var data = $("#uw-sec-token-form").serialize();
var data = $("#nw-sec-token-form").serialize();
// Cambiar el texto del botón a "Solicitando token"
changeButton(button, 'Solicitando token');
@@ -0,0 +1,28 @@
$(document).ready(function() {
$('.add-to-cart').on('click', function() {
var itemId = $(this).data('item-id');
$.post('/store/add_to_cart/', {item_id: itemId}, function(response) {
alert(response.message);
location.reload();
});
});
$('.remove-from-cart').on('click', function() {
var cartId = $(this).data('cart-id');
$.post('/store/remove_from_cart/', {cart_id: cartId}, function(response) {
alert(response.message);
location.reload();
});
});
$('#checkout-button').on('click', function() {
$.post('/store/checkout/', {}, function(response) {
if (response.success) {
var stripe = Stripe(response.stripe_public_key);
stripe.redirectToCheckout({ sessionId: response.session_id });
} else {
alert(response.message);
}
});
});
});
@@ -1,4 +1,4 @@
if(window.history.replaceState){window.history.replaceState(null,null,window.location.href);};$(function(){$('select').on('change',function(){var select=$(this);select.css('color',select.children('option:selected').css('color'));});});$(function(){$('#trade-sell-a').on('click',function(){$('#trade-sell-div').fadeIn('slow');$('#trade-buy-div').hide();});$('#trade-buy-a').on('click',function(){$('#trade-buy-div').fadeIn('slow');$('#trade-sell-div').hide();});});$(function(){$(".toggle-password").click(function(){$(this).toggleClass("fa-eye fa-eye-slash");var type=$(this).hasClass("fa-eye-slash")?"text":"password";$("#password-sell").attr("type",type);});});$(function(){$(".toggle-password").click(function(){$(this).toggleClass("fa-eye fa-eye-slash");var type=$(this).hasClass("fa-eye-slash")?"text":"password";$("#password-buy").attr("type",type);});});$(function(){$(".toggle-token").click(function(){$(this).toggleClass("fa-eye fa-eye-slash");var type=$(this).hasClass("fa-eye-slash")?"text":"password";$("#security-token-sell").attr("type",type);});});$(function(){$(".toggle-token").click(function(){$(this).toggleClass("fa-eye fa-eye-slash");var type=$(this).hasClass("fa-eye-slash")?"text":"password";$("#security-token-buy").attr("type",type);});});$(function(){$('.trade-points-sell-button').on('click',function(e){e.preventDefault();e.stopPropagation();$("#trade-points-sell-response").empty();var button=$(this);var buttonoriginal=button.html();var data={tradepointssell:button.data('id')};data=$("#uw-trade-points-sell-form").serialize()+'&'+$.param(data);changeButton(button,'CREANDO CÓDIGO');$.ajax({type:'POST',url:'',data:data,dataType:'json',success:function(data){$("#trade-points-sell-response").append(data.message).hide().slideDown();if(data.success===true){button.html("CÓDIGO CREADO");button.css("color","#d79602");setTimeout(function(){$("#uw-trade-points-sell-form")[0].reset();restoreButton(button,buttonoriginal);grecaptcha.reset(0);},5000);}
else{setTimeout(function(){$("#trade-points-sell-response").slideUp(function(){$("#trade-points-sell-response").empty();restoreButton(button,buttonoriginal);grecaptcha.reset(0);});},5000);}},error:function(){setTimeout(function(){alert("Algo ha salido mal. Por favor intente más tarde");window.location.reload();},2000);}});});});$(function(){$('.trade-points-buy-button').on('click',function(e){e.preventDefault();e.stopPropagation();$("#trade-points-buy-response").empty();$(".trade-points-check-button").prop('disabled',true);var button=$(this);var buttonoriginal=button.html();var data={tradepointsbuy:button.data('id')};data=$("#uw-trade-points-buy-form").serialize()+'&'+$.param(data);changeButton(button,'CANJEANDO CÓDIGO');$.ajax({type:'POST',url:'',data:data,dataType:'json',success:function(data){$("#trade-points-buy-response").append(data.message).hide().slideDown();if(data.success===true){button.html("CÓDIGO CANJEADO");button.css("color","#d79602");setTimeout(function(){$("#uw-trade-points-buy-form")[0].reset();$(".trade-points-check-button").prop('disabled',false);restoreButton(button,buttonoriginal);grecaptcha.reset(1);},5000);}
else{setTimeout(function(){$("#trade-points-buy-response").slideUp(function(){$("#trade-points-buy-response").empty();$(".trade-points-check-button").prop('disabled',false);restoreButton(button,buttonoriginal);grecaptcha.reset(1);});},5000);}},error:function(){setTimeout(function(){alert("Algo ha salido mal. Por favor intente más tarde");window.location.reload();},2000);}});});});$(function(){$('.trade-points-check-button').on('click',function(e){e.preventDefault();e.stopPropagation();$("#trade-points-buy-response").empty();$(".trade-points-buy-button").prop('disabled',true);var button=$(this);var buttonoriginal=button.html();var data={tradepointscheck:button.data('id')};data=$("#uw-trade-points-buy-form").serialize()+'&'+$.param(data);changeButton(button,'CHEQUEANDO CÓDIGO');$.ajax({type:'POST',url:'',data:data,dataType:'json',success:function(data){$("#trade-points-buy-response").append(data.message).hide().slideDown();if(data.success===true){button.html("INFO DEL CÓDIGO");button.css("color","#d79602");setTimeout(function(){$(".trade-points-buy-button").prop('disabled',false);restoreButton(button,buttonoriginal);grecaptcha.reset(1);},5000);}
if(window.history.replaceState){window.history.replaceState(null,null,window.location.href);};$(function(){$('select').on('change',function(){var select=$(this);select.css('color',select.children('option:selected').css('color'));});});$(function(){$('#trade-sell-a').on('click',function(){$('#trade-sell-div').fadeIn('slow');$('#trade-buy-div').hide();});$('#trade-buy-a').on('click',function(){$('#trade-buy-div').fadeIn('slow');$('#trade-sell-div').hide();});});$(function(){$(".toggle-password").click(function(){$(this).toggleClass("fa-eye fa-eye-slash");var type=$(this).hasClass("fa-eye-slash")?"text":"password";$("#password-sell").attr("type",type);});});$(function(){$(".toggle-password").click(function(){$(this).toggleClass("fa-eye fa-eye-slash");var type=$(this).hasClass("fa-eye-slash")?"text":"password";$("#password-buy").attr("type",type);});});$(function(){$(".toggle-token").click(function(){$(this).toggleClass("fa-eye fa-eye-slash");var type=$(this).hasClass("fa-eye-slash")?"text":"password";$("#security-token-sell").attr("type",type);});});$(function(){$(".toggle-token").click(function(){$(this).toggleClass("fa-eye fa-eye-slash");var type=$(this).hasClass("fa-eye-slash")?"text":"password";$("#security-token-buy").attr("type",type);});});$(function(){$('.trade-points-sell-button').on('click',function(e){e.preventDefault();e.stopPropagation();$("#trade-points-sell-response").empty();var button=$(this);var buttonoriginal=button.html();var data={tradepointssell:button.data('id')};data=$("#nw-trade-points-sell-form").serialize()+'&'+$.param(data);changeButton(button,'CREANDO CÓDIGO');$.ajax({type:'POST',url:'',data:data,dataType:'json',success:function(data){$("#trade-points-sell-response").append(data.message).hide().slideDown();if(data.success===true){button.html("CÓDIGO CREADO");button.css("color","#d79602");setTimeout(function(){$("#nw-trade-points-sell-form")[0].reset();restoreButton(button,buttonoriginal);grecaptcha.reset(0);},5000);}
else{setTimeout(function(){$("#trade-points-sell-response").slideUp(function(){$("#trade-points-sell-response").empty();restoreButton(button,buttonoriginal);grecaptcha.reset(0);});},5000);}},error:function(){setTimeout(function(){alert("Algo ha salido mal. Por favor intente más tarde");window.location.reload();},2000);}});});});$(function(){$('.trade-points-buy-button').on('click',function(e){e.preventDefault();e.stopPropagation();$("#trade-points-buy-response").empty();$(".trade-points-check-button").prop('disabled',true);var button=$(this);var buttonoriginal=button.html();var data={tradepointsbuy:button.data('id')};data=$("#nw-trade-points-buy-form").serialize()+'&'+$.param(data);changeButton(button,'CANJEANDO CÓDIGO');$.ajax({type:'POST',url:'',data:data,dataType:'json',success:function(data){$("#trade-points-buy-response").append(data.message).hide().slideDown();if(data.success===true){button.html("CÓDIGO CANJEADO");button.css("color","#d79602");setTimeout(function(){$("#nw-trade-points-buy-form")[0].reset();$(".trade-points-check-button").prop('disabled',false);restoreButton(button,buttonoriginal);grecaptcha.reset(1);},5000);}
else{setTimeout(function(){$("#trade-points-buy-response").slideUp(function(){$("#trade-points-buy-response").empty();$(".trade-points-check-button").prop('disabled',false);restoreButton(button,buttonoriginal);grecaptcha.reset(1);});},5000);}},error:function(){setTimeout(function(){alert("Algo ha salido mal. Por favor intente más tarde");window.location.reload();},2000);}});});});$(function(){$('.trade-points-check-button').on('click',function(e){e.preventDefault();e.stopPropagation();$("#trade-points-buy-response").empty();$(".trade-points-buy-button").prop('disabled',true);var button=$(this);var buttonoriginal=button.html();var data={tradepointscheck:button.data('id')};data=$("#nw-trade-points-buy-form").serialize()+'&'+$.param(data);changeButton(button,'CHEQUEANDO CÓDIGO');$.ajax({type:'POST',url:'',data:data,dataType:'json',success:function(data){$("#trade-points-buy-response").append(data.message).hide().slideDown();if(data.success===true){button.html("INFO DEL CÓDIGO");button.css("color","#d79602");setTimeout(function(){$(".trade-points-buy-button").prop('disabled',false);restoreButton(button,buttonoriginal);grecaptcha.reset(1);},5000);}
else{setTimeout(function(){$("#trade-points-buy-response").slideUp(function(){$("#trade-points-buy-response").empty();$(".trade-points-buy-button").prop('disabled',false);restoreButton(button,buttonoriginal);grecaptcha.reset(1);});},5000);}},error:function(){setTimeout(function(){alert("Algo ha salido mal. Por favor intente más tarde");window.location.reload();},2000);}});});});
@@ -0,0 +1,37 @@
$(function(){
$('.transfer-button').on('click', function(e) {
e.preventDefault();
$("#transfer-character-response").empty();
var button = $(this);
var originalText = button.text();
var data = $("#uw-transfer-character-form").serialize();
button.text("Procesando pago...");
button.prop("disabled", true);
$.ajax({
type: 'POST',
url: '', // URL de transferencia
data: data,
dataType: 'json',
success: function(response) {
if (response.success) {
var stripe = Stripe(response.stripe_public_key);
stripe.redirectToCheckout({
sessionId: response.session_id
});
} else {
$("#transfer-character-response").append(response.message).hide().slideDown();
button.text(originalText);
button.prop("disabled", false);
}
},
error: function() {
$("#transfer-character-response").append('<span class="red-form-response">Error inesperado. Intente más tarde.</span>').hide().slideDown();
button.text(originalText);
button.prop("disabled", false);
}
});
});
});
@@ -6,7 +6,7 @@ $(function() {
var button = $(this);
var originalText = button.html();
var data = $("#uw-unstuck-form").serialize();
var data = $("#nw-unstuck-form").serialize();
button.html("Desbloqueando...");
button.prop("disabled", true);
@@ -22,7 +22,7 @@ $(function() {
if (data.success) {
button.html("Desbloqueado");
setTimeout(function() {
$("#uw-unstuck-form")[0].reset();
$("#nw-unstuck-form")[0].reset();
button.html(originalText);
button.prop("disabled", false);
}, 5000);
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/change_faction.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/change_faction_cancel.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/change_faction_success.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
+9
View File
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/change_race.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/change_race_success.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/change_race_success.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/customize_character.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/customize_success.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
+9
View File
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/gold_cancel.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/gold_character.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
+9
View File
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/gold_success.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
+9
View File
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/level_up.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/level_up_cancel.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/level_up_success.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/rename_cancel.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/rename_character.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/rename_success.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/revive_character.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/store_novawow.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/transfer_cancel.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/transfer_character.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,9 @@
<!DOCTYPE html>
{% include 'partials/head.html' %}
{% include 'partials/header.html' %}
{% include 'partials/video.html' %}
{% include 'partials/transfer_success.html' %}
{% include 'partials/social.html' %}
{% include 'partials/footer.html' %}
{% include 'partials/final.html' %}
@@ -0,0 +1,77 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Cambiar facción del personaje</h1></div>
<div class="box-content">
<div class="title-box-content"><h2>Información</h2><a class="back-to-account" href="my-account">Regresar a mi cuenta</a><a class="back-to-account-responsive" href="my-account">Regresar</a></div>
<div class="body-box-content justified">
<br>
<p>La herramienta <span>Cambiar facción del personaje</span> te permite cambiar de la Alianza a la Horda y viceversa.</p>
<p>Si también deseas cambiar el nombre del personaje, debes usar la herramienta Renombrar personaje.</p>
<br>
<p>Al hacer un cambio de Facción:</p>
<p>- Los items, hechizos, títulos, reputaciones, monturas y logros se cambiarán a la nueva facción</p>
<p>- Las misiones activas en el Registro de misiones serán abandonadas</p>
<p>- Los teams de arena seán borrados</p>
<p>- Los amigos en la Lista de amigos se borrarán</p>
<br>
<p><span class="red-info2">Restricciones del personaje:</span></p>
<p>- No debe tener subastas activas</p>
<p>- No debe tener correos en el buzón</p>
<p>- No debe capitán de un team de arenas</p>
<p>- No debe ser miembro de una hermandad</p>
<p>- No debe tener demasiado oro</p>
<br>
<table class="max-gold-table">
<tbody><tr>
<th>Nivel</th>
<th>Max. Oro</th>
</tr>
<tr>
<td>10-30</td>
<td>300<img src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-images/nw-icons/money-gold.gif" width="10px"></td>
</tr>
<tr>
<td>31-50</td>
<td>1000<img src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-images/nw-icons/money-gold.gif" width="10px"></td>
</tr>
<tr>
<td>51-70</td>
<td>5000<img src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-images/nw-icons/money-gold.gif" width="10px"></td>
</tr>
<tr>
<td>71-80</td>
<td>20000<img src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-images/nw-icons/money-gold.gif" width="10px"></td>
</tr>
</tbody></table>
<br>
<p>Al usar el botón CAMBIAR FACCIÓN del personaje que hayas escogido, se enviará una petición de cambio de facción de dicho personaje.</p>
<p>Cuando ingreses a la lista de personajes de tu cuenta, verás un ícono a la izquierda de tu personaje escogido.</p>
<p>Al darle click a dicho ícono ingresarás al menú de edición de personaje que te permitirá pasar a la facción contraria.</p>
<br>
<fieldset>
<legend>NOTA</legend>
<div class="separate2">
<p>Por favor, asegúrate de haber escogido al personaje correcto ya que esta acción no es reversible una vez realizada.</p>
</div>
</fieldset>
<form action="" id="nw-change-faction-form" method="POST" accept-charset="utf-8">
<select name="character">
<option value="" selected disabled>Seleccione un personaje</option>
{% for character in characters %}
<option class="priest big-font" value="{{ character }}">{{ character }}</option>
{% endfor %}
</select>
<br>
<button class="change-faction-button" type="submit" name="change-faction-button" data-id="ChangeFaction">Cambiar Facción por {{ price }} €</button>
</form>
<br>
<hr>
<center><div class="alert-message" id="change-race-response"></div></center>
<br>
</div>
</div>
</div>
</div>
</div>
+46
View File
@@ -0,0 +1,46 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Cambiar raza del personaje</h1></div>
<div class="box-content">
<div class="title-box-content"><h2>Información</h2><a class="back-to-account" href="my-account">Regresar a mi cuenta</a><a class="back-to-account-responsive" href="my-account">Regresar</a></div>
<div class="body-box-content justified">
<br>
<p>La herramienta <span>Cambiar raza del personaje</span> te permite cambiar la raza del personaje entre otras de la misma facción.</p>
<p>Si también deseas cambiar el nombre del personaje, debes usar la herramienta Renombrar personaje.</p>
<br>
<p>Al usar el botón CAMBIAR RAZA del personaje que hayas escogido, se enviará una petición de cambio de raza de dicho personaje.</p>
<p>Cuando ingreses a la lista de personajes de tu cuenta, verás un ícono a la izquierda de tu personaje escogido.</p>
<p>Al darle click a dicho ícono ingresarás al menú de edición de personaje que te permitirá escoger entre las razas de la misma facción.</p>
<br>
<fieldset>
<legend>NOTA</legend>
<div class="separate2">
<p>Por favor, asegúrate de haber escogido al personaje correcto ya que esta acción no es reversible una vez realizada.</p>
</div>
</fieldset>
<form id="nw-change-race-form" div class="centered">
<br>
<br>
<p>Escoge el personaje que quieres desbloquear</p>
<br>
<form action="" id="nw-change-race-form" method="POST" accept-charset="utf-8">
<select name="character">
<option value="" selected disabled>Seleccione un personaje</option>
{% for character in characters %}
<option class="priest big-font" value="{{ character }}">{{ character }}</option>
{% endfor %}
</select>
<br>
<button class="change-race-button" type="submit" name="change-race-button" data-id="ChangeRace">Cambiar Raza por {{ price }} €</button>
</form>
<br>
<hr>
<center><div class="alert-message" id="change-race-response"></div></center>
<br>
</div>
</div>
</div>
</div>
</div>
</div>
@@ -0,0 +1 @@
@@ -0,0 +1,51 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Personalizar personaje</h1></div>
<div class="box-content">
<div class="title-box-content"><h2>Información</h2><a class="back-to-account" href="my-account">Regresar a mi cuenta</a><a class="back-to-account-responsive" href="my-account">Regresar</a></div>
<div class="body-box-content justified">
<br>
<p>La herramienta <span>Personalizar personaje</span> te permite cambiar los siguientes aspectos un personaje:</p>
<p>- Color de la piel</p>
<p>- Rostro</p>
<p>- Pelo</p>
<p>- Sexo</p>
<p>- Características correspondientes a cada raza como cuernos, pendientes, marcas, vello facial</p>
<p>Si también deseas cambiar el nombre del personaje, debes usar la herramienta Renombrar personaje.</p>
<br>
<p>Al usar el botón PERSONALIZAR del personaje que hayas escogido, se enviará una petición de personalización de dicho personaje.</p>
<p>Cuando ingreses a la lista de personajes de tu cuenta, verás un ícono a la izquierda de tu personaje escogido.</p>
<p>Al darle click a dicho ícono ingresarás al menú de edición de personaje que te permitirá escoger diferentes características.</p>
<br>
<fieldset>
<legend>NOTA</legend>
<div class="separate2">
<p>Por favor, asegúrate de haber escogido al personaje correcto ya que esta acción no es reversible una vez realizada.</p>
</div>
</fieldset>
<form id="nw-customize-form" div class="centered">
<br>
<br>
<p>Escoge el personaje que quieres desbloquear</p>
<br>
<form action="" id="nw-customize-form" method="POST" accept-charset="utf-8">
<select name="character">
<option value="" selected disabled>Seleccione un personaje</option>
{% for character in characters %}
<option class="priest big-font" value="{{ character }}">{{ character }}</option>
{% endfor %}
</select>
<br>
<button class="customize-button" type="submit" name="rename-button" data-id="Renombrar">Renombrar por {{ price }} €</button>
</form>
<br>
<hr>
<center><div class="alert-message" id="customize-response"></div></center>
<br>
</div>
</div>
</div>
</div>
</div>
</div>
@@ -0,0 +1,44 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Personalizar personaje</h1></div>
<div class="box-content">
<div class="title-box-content"><h2>Información</h2><a class="back-to-account" href="my-account">Regresar a mi cuenta</a><a class="back-to-account-responsive" href="my-account">Regresar</a></div>
<div class="body-box-content justified">
<br>
<p>La herramienta <span>Personalizar personaje</span> te permite cambiar los siguientes aspectos un personaje:</p>
<p>- Color de la piel</p>
<p>- Rostro</p>
<p>- Pelo</p>
<p>- Sexo</p>
<p>- Características correspondientes a cada raza como cuernos, pendientes, marcas, vello facial</p>
<p>Si también deseas cambiar el nombre del personaje, debes usar la herramienta Renombrar personaje.</p>
<br>
<p>Al usar el botón PERSONALIZAR del personaje que hayas escogido, se enviará una petición de personalización de dicho personaje.</p>
<p>Cuando ingreses a la lista de personajes de tu cuenta, verás un ícono a la izquierda de tu personaje escogido.</p>
<p>Al darle click a dicho ícono ingresarás al menú de edición de personaje que te permitirá escoger diferentes características.</p>
<br>
<fieldset>
<legend>NOTA</legend>
<div class="separate2">
<p>Por favor, asegúrate de haber escogido al personaje correcto ya que esta acción no es reversible una vez realizada.</p>
</div>
</fieldset>
<div class="body-box-content justified">
<p>Selecciona el personaje que deseas personalizar:</p>
<form id="nw-customize-form">
<select name="character" required>
<option value="" selected disabled>Seleccione un personaje</option>
{% for character in characters %}
<option value="{{ character }}">{{ character }}</option>
{% endfor %}
</select>
<button type="button" class="customize-button">Personalizar por {{ price }} €</button>
</form>
<div id="customize-response"></div>
</div>
</div>
</div>
</div>
</div>
</div>
+2 -2
View File
@@ -190,7 +190,7 @@
<input type="hidden" name="business" value="cgc.jail@gmail.com">
<input type="hidden" name="return" value="https://ultimowow.com/es/my-account">
<input type="hidden" name="cancel_return" value="https://ultimowow.com/es/my-account">
<input type="hidden" name="notify_url" value="https://ultimowow.com/es/uw-paypal/paypal_ipn_lib">
<input type="hidden" name="notify_url" value="https://ultimowow.com/es/nw-paypal/paypal_ipn_lib">
<!--<script>
const numberInput = document.getElementById("pp-input-value");
let number = numberInput.value;
@@ -283,7 +283,7 @@
<p class="centered second-brown">Valor mínimo por transacción: $2</p>
<br>
<p class="centered">Cantidad en USD a adquirir</p>
<form class="centered" id="dlocal-form" action="uw-dlocalgo/dlocal_notification" method="post">
<form class="centered" id="dlocal-form" action="nw-dlocalgo/dlocal_notification" method="post">
<input type="number" placeholder="Cantidad en USD" min="2" step="1" pattern="[0-9]" id="cantidad" name="cantidad" required=""> USD
<input type="hidden" id="username" name="username" value="INNAPMINE">
<br>
+1 -1
View File
@@ -56,7 +56,7 @@
<div class="body-box-content justified">
{{ download_content.content|safe }}
<div class="centered">
<form name="uw-client-dowload" id="uw-client-download" method="post" autocomplete="off">
<form name="nw-client-dowload" id="nw-client-download" method="post" autocomplete="off">
<p><span>Idioma</span></p>
<br>
<select name="game-language" id="game-language" class="game-download-select" onchange="mostrarSistemasOperativos();">
@@ -0,0 +1,32 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Adquirir oro</h1></div>
<div class="box-content">
<div class="title-box-content">
<h2>Información</h2>
<a class="back-to-account" href="{% url 'my-account' %}">Regresar a mi cuenta</a>
</div>
<div class="body-box-content justified">
<p>Selecciona un personaje y la cantidad de oro:</p>
<form id="uw-gold-form">
<select name="character" required>
<option value="" selected disabled>Seleccione un personaje</option>
{% for character, data in characters.items %}
<option value="{{ character }}">{{ character }}</option>
{% endfor %}
</select>
<select name="gold_amount" required>
<option value="" selected disabled>Seleccione cantidad de oro</option>
{% for price in gold_prices %}
<option value="{{ price.gold_amount }}">{{ price.gold_amount }} oro - {{ price.price }} EUR</option>
{% endfor %}
</select>
<button type="button" class="gold-button">Enviar oro</button>
</form>
<div id="gold-response"></div>
</div>
</div>
</div>
</div>
</div>
+10
View File
@@ -53,6 +53,16 @@
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/rename_guild_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/vote_points_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/unstuck_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/revive_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/rename_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/customize_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/change_race_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/change_faction_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/level_up_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/gold_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/transfer_character_response.js"></script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js-handlers/store_response.js"></script>
<script src="https://js.stripe.com/v3/"></script>
<script>var aowow_tooltips = { "colorlinks": true, "iconizelinks": true, "renamelinks": true }</script>
<script src="{{ URL_PRINCIPAL }}/static/nw-themes/nw-ryu/nw-js/nw-scripts.js"></script>
+42
View File
@@ -0,0 +1,42 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Subir a nivel 80</h1></div>
<div class="box-content">
<div class="title-box-content"><h2>Información</h2><a class="back-to-account" href="my-account">Regresar a mi cuenta</a><a class="back-to-account-responsive" href="my-account">Regresar</a></div>
<div class="body-box-content justified">
<br>
<p>La herramienta <span>Subir a nivel 80</span> te permite subir cualquier personaje al nivel 80.</p>
<p>Sólo subirá de nivel al personaje. Esta opción no incluye ítems/oro/etc.</p>
<br>
<p>Al usar el botón SUBIR A NIVEL 80 del personaje que hayas escogido, se enviará el nivel 80 al personaje.</p>
<p>Cuando ingreses a la lista de personajes de tu cuenta, verás que tu personaje escogido ya es nivel 80.</p>
<br>
<fieldset>
<legend>NOTA</legend>
<div class="separate2">
<p>Se requiere que el personaje esté desconectado.</p>
<p>Por favor, asegúrate de haber escogido al personaje correcto ya que esta acción no es reversible una vez realizada.</p>
</div>
</fieldset>
<p>Selecciona el personaje que deseas subir al nivel 80:</p>
<form action="" id="nw-levelup-form" method="POST" accept-charset="utf-8">
<select name="character">
<option value="" selected disabled>Seleccione un personaje</option>
{% for character in characters %}
<option class="priest big-font" value="{{ character }}">{{ character }}</option>
{% endfor %}
</select>
<br>
<button class="level-up-button" type="submit" name="level-up-button" data-id="LevelUp">Subir a nivel 80 por {{ price }} €</button>
</form>
<br>
<hr>
<center><div class="alert-message" id="levelup-response"></div></center>
<br>
</div>
</div>
</div>
</div>
</div>
+1 -1
View File
@@ -372,7 +372,7 @@
</tr>
<tr>
<td>
<a href="store-bennu">
<a href="store-novawow">
<div class="tool-button">
<div class="acc-icon store-icon"></div>
<div class="tool-button-div">
+3 -3
View File
@@ -32,7 +32,7 @@
<option value="recover-accountname-form">Nombre de cuenta</option>
<option value="recover-activationlink-form">Enlace de activación</option>
</select>
</p><form action="" method="POST" id="uw-recover-accountpassword-form" accept-charset="utf-8" style="">
</p><form action="" method="POST" id="nw-recover-accountpassword-form" accept-charset="utf-8" style="">
<table class="middle-center-table">
<tbody><tr>
<td><input type="text" maxlength="20" name="username" id="username" placeholder="Nombre de usuario"></td>
@@ -45,7 +45,7 @@
</tr>
</tbody></table>
</form>
<form action="" method="POST" id="uw-recover-accountname-form" accept-charset="utf-8" style="display: none;">
<form action="" method="POST" id="nw-recover-accountname-form" accept-charset="utf-8" style="display: none;">
<table class="middle-center-table">
<tbody><tr>
<td><input type="email" name="email" id="email" placeholder="Correo electrónico"></td>
@@ -58,7 +58,7 @@
</tr>
</tbody></table>
</form>
<form action="" method="POST" id="uw-recover-activationlink-form" accept-charset="utf-8" style="display: none;">
<form action="" method="POST" id="nw-recover-activationlink-form" accept-charset="utf-8" style="display: none;">
<table class="middle-center-table">
<tbody><tr>
<td><input type="text" maxlength="20" name="username" id="username" placeholder="Nombre de usuario"></td>
+3 -3
View File
@@ -5,7 +5,7 @@
function checkAdBlocker() {
let adBlockerDetected = false;
const testAdURL = "https://ultimowow.com/es/uw-js-handlers/openad.js";
const testAdURL = "https://ultimowow.com/es/nw-js-handlers/openad.js";
const xhr = new XMLHttpRequest();
xhr.open("GET", testAdURL, false);
try {
@@ -62,7 +62,7 @@
function checkAdBlocker() {
let adBlockerDetected = false;
const testAdURL = "https://ultimowow.com/es/uw-js-handlers/openad.js";
const testAdURL = "https://ultimowow.com/es/nw-js-handlers/openad.js";
const xhr = new XMLHttpRequest();
xhr.open("GET", testAdURL, false);
try {
@@ -104,7 +104,7 @@
<div class="box-content">
<div class="body-box-content centered">
<form action="" method="POST" id="uw-create-form" accept-charset="utf-8">
<form action="" method="POST" id="nw-create-form" accept-charset="utf-8">
<table class="middle-center-table">
<tbody><tr>
<td><input type="text" maxlength="17" name="username" id="username" placeholder="Nombre de usuario"></td>
@@ -0,0 +1,34 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Renombrar personaje</h1></div>
<div class="box-content">
<div class="title-box-content"><h2>Información</h2><a class="back-to-account" href="my-account">Regresar a mi cuenta</a><a class="back-to-account-responsive" href="my-account">Regresar</a></div>
<div class="body-box-content justified">
<br>
<p>La herramienta <span>Renombrar personaje</span> te permite Renombrar un personaje el nombre se cambiara en el proximo inicio de session.</p>
<p>Usa esta opción cuando quieras cambiar el nombre del personaje.</p>
<br>
<fieldset>
<legend>NOTA</legend>
<div class="separate2">
<p>Se requiere que el personaje esté desconectado.</p>
<p>Se puede repetir la acción las veces que quieras.</p>
</div>
</fieldset>
<form id="nw-rename-form" div class="centered">
<br>
<br>
<p>Escoge el personaje que quieres renombrar</p>
<br>
<br>
<hr>
<span class="red-form-response">El pago ha sido cancelado. No se realizó ningún cambio.</span>
<br>
</div>
</div>
</div>
</div>
</div>
</div>
@@ -0,0 +1,43 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Renombrar personaje</h1></div>
<div class="box-content">
<div class="title-box-content"><h2>Información</h2><a class="back-to-account" href="my-account">Regresar a mi cuenta</a><a class="back-to-account-responsive" href="my-account">Regresar</a></div>
<div class="body-box-content justified">
<br>
<p>La herramienta <span>Renombrar personaje</span> te permite Renombrar un personaje el nombre se cambiara en el proximo inicio de session.</p>
<p>Usa esta opción cuando quieras cambiar el nombre del personaje.</p>
<br>
<fieldset>
<legend>NOTA</legend>
<div class="separate2">
<p>Se requiere que el personaje esté desconectado.</p>
<p>Se puede repetir la acción en un mismo las veces que quieras.</p>
</div>
</fieldset>
<form id="nw-rename-form" div class="centered">
<br>
<br>
<p>Escoge el personaje que quieres desbloquear</p>
<br>
<form action="" id="nw-unstuck-form" method="POST" accept-charset="utf-8">
<select name="character">
<option value="" selected disabled>Seleccione un personaje</option>
{% for character in characters %}
<option class="priest big-font" value="{{ character }}">{{ character }}</option>
{% endfor %}
</select>
<br>
<button class="rename-button" type="submit" name="rename-button" data-id="Renombrar">Renombrar por {{ price }} €</button>
</form>
<br>
<hr>
<center><div class="alert-message" id="rename-response"></div></center>
<br>
</div>
</div>
</div>
</div>
</div>
</div>
@@ -0,0 +1,39 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content">
<h1>Revivir personaje</h1>
</div>
<div class="box-content">
<div class="title-box-content">
<h2>Información</h2>
<a class="back-to-account" href="{% url 'my-account' %}">Regresar a mi cuenta</a>
<a class="back-to-account-responsive" href="{% url 'my-account' %}">Regresar</a>
</div>
<div class="body-box-content justified">
<br>
{% if characters %}
<p>Escoge el personaje que quieres revivir:</p>
<br>
<form id="nw-revive-form" action="" method="POST" accept-charset="utf-8">
{% csrf_token %}
<select name="character">
<option disabled selected value="">Seleccione un personaje</option>
{% for character in characters %}
<option value="{{ character }}">{{ character }}</option>
{% endfor %}
</select>
<br>
<button class="revive-button" type="submit" name="revive" data-id="Revivir">Revivir</button>
</form>
<br>
{% else %}
<p>No hay personajes disponibles para revivir.</p>
{% endif %}
<hr>
<div class="alert-message" id="revive-response"></div>
</div>
</div>
</div>
</div>
</div>
@@ -0,0 +1,32 @@
<div class="main-page">
<div class="store-categories">
{% for category in categories %}
<h2>{{ category.name }}</h2>
<ul>
{% for item in category.storeitem_set.all %}
<li>
<img src="{{ item.image_url }}" alt="{{ item.name }}">
<p>{{ item.name }}</p>
<p>{{ item.price }} €</p>
<button class="add-to-cart" data-item-id="{{ item.id }}">Añadir</button>
</li>
{% endfor %}
</ul>
{% endfor %}
</div>
<div class="cart">
<h2>Carrito</h2>
<ul>
{% for cart_item in cart_items %}
<li>
<p>{{ cart_item.item.name }}</p>
<p>{{ cart_item.item.price }} €</p>
<button class="remove-from-cart" data-cart-id="{{ cart_item.id }}">Eliminar</button>
</li>
{% endfor %}
</ul>
<p>Total: {{ total_price }} €</p>
<button id="checkout-button">Pagar</button>
</div>
</div>
+2 -2
View File
@@ -56,7 +56,7 @@
<button id="trade-buy-a" class="trade-option-button">COMPRA</button>
<br>
<div id="trade-sell-div">
<form action="" method="POST" id="uw-trade-points-sell-form" accept-charset="utf-8">
<form action="" method="POST" id="nw-trade-points-sell-form" accept-charset="utf-8">
<table class="middle-center-table">
<tbody><tr>
<td>¿Cuánto valdrá el código en PD?</td>
@@ -102,7 +102,7 @@
<div class="alert-message" id="trade-points-sell-response"></div>
</div>
<div id="trade-buy-div">
<form action="" method="POST" id="uw-trade-points-buy-form" accept-charset="utf-8">
<form action="" method="POST" id="nw-trade-points-buy-form" accept-charset="utf-8">
<table class="middle-center-table">
<tbody><tr>
<td>Ingresa el ID del código de PD</td>
@@ -0,0 +1,28 @@
<div class="main-page">
<div class="middle-content">
<div class="body-content">
<div class="title-content"><h1>Transferir personaje</h1></div>
<div class="box-content">
<div class="title-box-content">
<h2>Información</h2>
<a class="back-to-account" href="{% url 'my-account' %}">Regresar a mi cuenta</a>
</div>
<div class="body-box-content justified">
<form id="uw-transfer-character-form">
<select name="character" required>
<option value="" selected disabled>Seleccione un personaje</option>
{% for character in characters %}
<option value="{{ character.0 }}">{{ character.0 }}</option>
{% endfor %}
</select>
<input type="text" name="destination_account" placeholder="Cuenta destino" required>
<input type="password" name="security_token" placeholder="Token de seguridad" required>
<button type="button" class="transfer-button">Transferir por {{ price }} €</button>
</form>
<hr>
<center><div id="transfer-character-response"></div></center>
</div>
</div>
</div>
</div>
</div>
@@ -22,7 +22,7 @@
</fieldset>
<div class="centered">
<p>Escoge el personaje que quieres desbloquear</p>
<form id="uw-unstuck-form" method="POST" accept-charset="utf-8">
<form id="nw-unstuck-form" method="POST" accept-charset="utf-8">
{% csrf_token %}
<select name="character" required>
<option disabled selected value="">Selecciona un personaje</option>
+28
View File
@@ -41,6 +41,34 @@ urlpatterns = [
path('help', views.help_view, name='help'),
path('novawow-players', views.novawow_players_view, name='novawow_players'),
path('unstuck-character/', views.unstuck_character_view, name='unstuck-character'),
path('revive-character/', views.revive_character_view, name='revive-character'),
path('rename-character/', views.rename_character_view, name='rename-character'),
path('rename-success/', views.rename_success_view, name='rename-success'),
path('rename-cancel/', views.rename_cancel_view, name='rename-cancel'),
path('customize-character/', views.customize_character_view, name='customize-character'),
path('customize-success/', views.customize_success_view, name='customize-success'),
path('customize-cancel/', views.customize_cancel_view, name='customize-cancel'),
path('change-race-character/', views.change_race_character_view, name ='change-race-character'),
path('change-race-success/', views.change_race_success_view, name='change-race-success'),
path('change-race-cancel/' , views.change_race_cancel_view, name='change-race-cancel'),
path('change-faction-character/', views.change_faction_character_view, name='change-faction-character'),
path('change-faction-success/', views.change_faction_success_view, name='change-faction-success'),
path('change-faction-cancel/' , views.change_faction_cancel_view, name='change-faction-cancel'),
path('level-up-character/', views.level_up_character_view, name='level_up_character'),
path('level-up-success/', views.level_up_success_view, name='level-up-success'),
path('level-up-cancel/' , views.level_up_cancel_view, name='level-up-cancel'),
path('gold-character/' , views.gold_character_view, name='gold-character'),
path('gold-success/' , views.gold_success_view, name='gold-success'),
path('gold-cancel/' , views.gold_cancel_view, name='gold-cancel'),
path('transfer-character/' , views.transfer_character_view, name='transfer-character'),
path('transfer-success/' , views.transfer_success_view, name='transfer-success'),
path('transfer-cancel/' , views.transfer_cancel_view, name='transfer-cancel'),
path('store-novawow/' , views.store_novawow_view, name='store-novawow'),
]
+736 -2
View File
@@ -11,7 +11,8 @@ from django.db import connections
from django.contrib import messages
from django.contrib.auth import logout
from django import forms
from .models import Noticia, ClienteCategoria, ServerSelection, RecruitAFriend, DownloadClientPage, ContentCreator, RecruitReward, ClaimedReward, AccountActivation, SecurityToken, GuildRenameSettings, VoteSite, VoteLog, HomeApiPoints, UnstuckHistory
from .pagos_stripe import create_checkout_session
from .models import Noticia, ClienteCategoria, ServerSelection, RecruitAFriend, DownloadClientPage, ContentCreator, RecruitReward, ClaimedReward, AccountActivation, SecurityToken, GuildRenameSettings, VoteSite, VoteLog, HomeApiPoints, UnstuckHistory, ReviveHistory, RenamePrice, CustomizePrice, ChangeRacePrice, ChangeFactionPrice, LevelUpPrice, GoldPrice, TransferPrice, StoreCategory, StoreItem, Cart
from django.views.decorators.csrf import csrf_exempt
import logging
from datetime import datetime, timedelta
@@ -586,7 +587,7 @@ def my_account(request):
# Si la sesión no tiene el usuario, redirigir al inicio de sesión
if not username:
return redirect('log-in')
return redirect('login')
is_logged_in = True # Si el usuario está en la sesión, asumimos que está conectado
@@ -1133,6 +1134,739 @@ def promo_code_view(request):
from django.utils.timezone import now
from datetime import timedelta
def rename_character_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
# Obtener personajes del usuario desde la base de datos `acore_characters`
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT name
FROM characters
WHERE account = (
SELECT id
FROM acore_auth.account
WHERE username = %s
)
""", [username])
characters = [row[0] for row in cursor.fetchall()]
# Obtener el precio del renombrado
price_obj = RenamePrice.objects.first()
price = price_obj.price if price_obj else 2.00
if request.method == 'POST':
character_name = request.POST.get('character')
# Validar si el personaje fue seleccionado
if not character_name:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Por favor, seleccione un personaje.</span>'})
# Verificar si el personaje pertenece al usuario
if character_name not in characters:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">No tienes permiso para renombrar este personaje.</span>'})
# Crear sesión de pago con Stripe
success_url = request.build_absolute_uri(reverse('rename-success'))
cancel_url = request.build_absolute_uri(reverse('rename-cancel'))
stripe_response = create_checkout_session(price, success_url=success_url, cancel_url=cancel_url)
if stripe_response["success"]:
request.session['rename_character'] = character_name
return JsonResponse({
'success': True,
'session_id': stripe_response["session_id"],
'stripe_public_key': settings.STRIPE_PUBLIC_KEY
})
else:
return JsonResponse({'success': False, 'message': f'<span class="red-form-response">Error al iniciar el pago: {stripe_response["error"]}</span>'})
return render(request, 'account/rename_character.html', {'characters': characters, 'price': price})
def rename_success_view(request):
# Procesar el comando SOAP tras el pago exitoso
character_name = request.session.get('rename_character')
if not character_name:
return redirect('rename-character')
command = f".char rename {character_name}"
response = execute_soap_command(command)
if response is None or response.strip() == "":
message = f"El personaje {character_name} ha sido marcado para renombrar."
request.session.pop('rename_character', None) # Limpiar la sesión
return render(request, 'account/rename_success.html', {'message': message})
else:
return render(request, 'account/rename_success.html', {'message': f"Error: {response}"})
def rename_cancel_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
return render(request, 'account/rename_cancel.html')
def customize_character_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
# Obtener personajes del usuario desde la base de datos `acore_characters`
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT name
FROM characters
WHERE account = (
SELECT id
FROM acore_auth.account
WHERE username = %s
)
""", [username])
characters = [row[0] for row in cursor.fetchall()]
# Obtener el precio de la personalización (si se gestiona desde el admin)
price_obj = CustomizePrice.objects.first()
price = price_obj.price if price_obj else 1.00
if request.method == 'POST':
character_name = request.POST.get('character')
# Validar si el personaje fue seleccionado
if not character_name:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Por favor, seleccione un personaje.</span>'})
# Verificar si el personaje pertenece al usuario
if character_name not in characters:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">No tienes permiso para personalizar este personaje.</span>'})
# Crear sesión de pago con Stripe
success_url = request.build_absolute_uri(reverse('customize-success'))
cancel_url = request.build_absolute_uri(reverse('customize-cancel'))
stripe_response = create_checkout_session(price, success_url=success_url, cancel_url=cancel_url)
if stripe_response["success"]:
# Guardar temporalmente el nombre del personaje en la sesión
request.session['customize_character'] = character_name
return JsonResponse({
'success': True,
'session_id': stripe_response["session_id"],
'stripe_public_key': settings.STRIPE_PUBLIC_KEY
})
else:
return JsonResponse({'success': False, 'message': f'<span class="red-form-response">Error al iniciar el pago: {stripe_response["error"]}</span>'})
return render(request, 'account/customize_character.html', {'characters': characters, 'price': price})
def customize_success_view(request):
# Procesar el comando SOAP tras el pago exitoso
character_name = request.session.get('customize_character')
if not character_name:
return redirect('customize-character')
command = f".char customi {character_name}"
response = execute_soap_command(command)
if response is None or response.strip() == "":
message = f"El personaje {character_name} ha sido marcado para personalización."
request.session.pop('customize_character', None) # Limpiar la sesión
return render(request, 'account/customize_success.html', {'message': message})
else:
return render(request, 'account/customize_success.html', {'message': f"Error: {response}"})
def customize_cancel_view(request):
return render(request, 'account/customize_cancel.html')
def change_race_character_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
# Obtener personajes del usuario desde la base de datos `acore_characters`
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT name
FROM characters
WHERE account = (
SELECT id
FROM acore_auth.account
WHERE username = %s
)
""", [username])
characters = [row[0] for row in cursor.fetchall()]
# Obtener el precio del cambio de raza
price_obj = ChangeRacePrice.objects.first()
price = price_obj.price if price_obj else 10.00 # Precio predeterminado si no hay registro
if request.method == 'POST':
character_name = request.POST.get('character')
# Validar si el personaje fue seleccionado
if not character_name:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Por favor, seleccione un personaje.</span>'})
# Verificar si el personaje pertenece al usuario
if character_name not in characters:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">No tienes permiso para cambiar la raza de este personaje.</span>'})
# Crear sesión de pago con Stripe
success_url = request.build_absolute_uri(reverse('change-race-success'))
cancel_url = request.build_absolute_uri(reverse('change-race-cancel'))
stripe_response = create_checkout_session(price, success_url=success_url, cancel_url=cancel_url)
if stripe_response["success"]:
# Guardar el personaje en la sesión para el cambio
request.session['change_race_character'] = character_name
return JsonResponse({
'success': True,
'session_id': stripe_response["session_id"],
'stripe_public_key': settings.STRIPE_PUBLIC_KEY
})
else:
return JsonResponse({'success': False, 'message': f'<span class="red-form-response">Error al iniciar el pago: {stripe_response["error"]}</span>'})
return render(request, 'account/change_race.html', {'characters': characters, 'price': price})
def change_race_success_view(request):
# Procesar el comando SOAP tras el pago exitoso
character_name = request.session.get('change_race_character')
if not character_name:
return redirect('change-race')
command = f".char changerace {character_name}"
response = execute_soap_command(command)
if response is None or response.strip() == "":
message = f"El personaje {character_name} ha sido marcado para cambio de raza."
request.session.pop('change_race_character', None) # Limpiar la sesión
return render(request, 'account/change_race_success.html', {'message': message})
else:
return render(request, 'account/change_race_success.html', {'message': f"Error: {response}"})
def change_race_cancel_view(request):
return render(request, 'account/change_race_cancel.html')
def change_faction_character_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
# Obtener personajes del usuario desde la base de datos `acore_characters`
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT name
FROM characters
WHERE account = (
SELECT id
FROM acore_auth.account
WHERE username = %s
)
""", [username])
characters = [row[0] for row in cursor.fetchall()]
# Obtener el precio del cambio de facción
price_obj = ChangeFactionPrice.objects.first()
price = price_obj.price if price_obj else 10.00
if request.method == 'POST':
character_name = request.POST.get('character')
# Validar si el personaje fue seleccionado
if not character_name:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Por favor, seleccione un personaje.</span>'})
# Verificar si el personaje pertenece al usuario
if character_name not in characters:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">No tienes permiso para cambiar la facción de este personaje.</span>'})
# Crear sesión de pago con Stripe
success_url = request.build_absolute_uri(reverse('change-faction-success'))
cancel_url = request.build_absolute_uri(reverse('change-faction-cancel'))
stripe_response = create_checkout_session(price, success_url=success_url, cancel_url=cancel_url)
if stripe_response["success"]:
# Guardar el personaje seleccionado en la sesión
request.session['change_faction_character'] = character_name
return JsonResponse({
'success': True,
'session_id': stripe_response["session_id"],
'stripe_public_key': settings.STRIPE_PUBLIC_KEY
})
else:
return JsonResponse({'success': False, 'message': f'<span class="red-form-response">Error al iniciar el pago: {stripe_response["error"]}</span>'})
return render(request, 'account/change_faction.html', {'characters': characters, 'price': price})
def change_faction_success_view(request):
# Procesar el comando SOAP tras el pago exitoso
character_name = request.session.get('change_faction_character')
if not character_name:
return redirect('change-faction-character')
command = f".char changef {character_name}"
response = execute_soap_command(command)
if response is None or response.strip() == "":
message = f"El personaje {character_name} ha cambiado de facción con éxito."
request.session.pop('change_faction_character', None) # Limpiar la sesión
return render(request, 'account/change_faction_success.html', {'message': message})
else:
return render(request, 'account/change_faction_success.html', {'message': f"Error: {response}"})
def change_faction_cancel_view(request):
return render(request, 'account/change_faction_cancel.html')
def level_up_character_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
# Obtener personajes del usuario desde la base de datos `acore_characters`
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT name
FROM characters
WHERE account = (
SELECT id
FROM acore_auth.account
WHERE username = %s
)
""", [username])
characters = [row[0] for row in cursor.fetchall()]
# Obtener el precio de subir a nivel 80
price_obj = LevelUpPrice.objects.first()
price = price_obj.price if price_obj else 10.00
if request.method == 'POST':
character_name = request.POST.get('character')
# Validar si el personaje fue seleccionado
if not character_name:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Por favor, seleccione un personaje.</span>'})
# Verificar si el personaje pertenece al usuario
if character_name not in characters:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">No tienes permiso para subir de nivel a este personaje.</span>'})
# Crear sesión de pago con Stripe
success_url = request.build_absolute_uri(reverse('level-up-success'))
cancel_url = request.build_absolute_uri(reverse('level-up-cancel'))
stripe_response = create_checkout_session(price, success_url=success_url, cancel_url=cancel_url)
if stripe_response["success"]:
# Guardar el personaje en la sesión para usarlo después del pago
request.session['levelup_character'] = character_name
return JsonResponse({
'success': True,
'session_id': stripe_response["session_id"],
'stripe_public_key': settings.STRIPE_PUBLIC_KEY
})
else:
return JsonResponse({'success': False, 'message': f'<span class="red-form-response">Error al iniciar el pago: {stripe_response["error"]}</span>'})
return render(request, 'account/level_up.html', {'characters': characters, 'price': price})
def level_up_success_view(request):
character_name = request.session.get('levelup_character')
if not character_name:
return redirect('level-up-character')
# Ejecutar el comando SOAP
command = f".char level {character_name} 80"
response = execute_soap_command(command)
if response is None or response.strip() == "":
message = f"El personaje {character_name} ha sido subido al nivel 80."
else:
message = f"Error: {response}"
# Limpiar la sesión
request.session.pop('levelup_character', None)
return render(request, 'account/level_up_success.html', {'message': message})
def level_up_cancel_view(request):
return render(request, 'account/level_up_cancel.html')
def gold_character_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
# Obtener personajes y estado de conexión del usuario
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT name, online, money
FROM characters
WHERE account = (
SELECT id
FROM acore_auth.account
WHERE username = %s
)
""", [username])
characters_data = cursor.fetchall()
characters = {row[0]: {'online': row[1], 'money': row[2]} for row in characters_data}
# Obtener precios del oro
gold_prices = GoldPrice.objects.all().order_by('gold_amount')
if request.method == 'POST':
character_name = request.POST.get('character')
gold_amount = request.POST.get('gold_amount')
# Validaciones iniciales
if not character_name or not gold_amount:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Seleccione un personaje y una cantidad de oro.</span>'})
if character_name not in characters:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">No tienes permiso para enviar oro a este personaje.</span>'})
if characters[character_name]['online'] == 1:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">El personaje debe estar desconectado para recibir oro.</span>'})
try:
gold_amount = int(gold_amount)
except ValueError:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Cantidad de oro no válida.</span>'})
gold_price = GoldPrice.objects.filter(gold_amount=gold_amount).first()
if not gold_price:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Cantidad de oro no válida.</span>'})
# Convertir el precio a formato que Stripe acepta (en centavos)
stripe_price = int(float(gold_price.price) * 1)
# Crear sesión de pago con Stripe
success_url = request.build_absolute_uri(reverse('gold-success'))
cancel_url = request.build_absolute_uri(reverse('gold-cancel'))
stripe_response = create_checkout_session(stripe_price, success_url=success_url, cancel_url=cancel_url)
if stripe_response["success"]:
# Guardar en sesión los datos para el callback tras el pago
request.session['gold_transaction'] = {
'character_name': character_name,
'gold_amount': gold_amount
}
return JsonResponse({
'success': True,
'session_id': stripe_response["session_id"],
'stripe_public_key': settings.STRIPE_PUBLIC_KEY
})
else:
return JsonResponse({'success': False, 'message': f'<span class="red-form-response">Error al iniciar el pago: {stripe_response["error"]}</span>'})
return render(request, 'account/gold_character.html', {'characters': characters, 'gold_prices': gold_prices})
def gold_success_view(request):
# Procesar el pago exitoso
transaction = request.session.pop('gold_transaction', None)
if not transaction:
return redirect('gold-character')
character_name = transaction['character_name']
gold_amount = int(transaction['gold_amount'])
# Calcular el oro en formato del juego
game_gold_amount = gold_amount * 10000
# Actualizar la cantidad de oro en la base de datos
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
UPDATE characters
SET money = money + %s
WHERE name = %s
""", [game_gold_amount, character_name])
return render(request, 'account/gold_success.html', {'character_name': character_name, 'gold_amount': gold_amount})
def gold_cancel_view(request):
return render(request, 'account/gold_cancel.html')
def transfer_character_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
# Obtener el precio de transferencia
price_obj = TransferPrice.objects.first()
price = price_obj.price if price_obj else 10.00
# Obtener el ID de usuario desde acore_auth.account
with connections['acore_auth'].cursor() as cursor:
cursor.execute("SELECT id FROM account WHERE username = %s", [username])
user_data = cursor.fetchone()
if not user_data:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Cuenta no encontrada. Por favor, inicie sesión nuevamente.</span>'})
user_id = user_data[0] # ID de la cuenta
# Obtener personajes de la cuenta de origen
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT name, class, online
FROM characters
WHERE account = %s
""", [user_id])
characters = cursor.fetchall()
if request.method == 'POST':
character_name = request.POST.get('character')
destination_account = request.POST.get('destination_account')
token = request.POST.get('security_token')
# Validaciones
if not all([character_name, destination_account, token]):
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Por favor, complete todos los campos.</span>'})
character = next((char for char in characters if char[0] == character_name), None)
if not character:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">No tienes permiso para transferir este personaje.</span>'})
# Verificar si el personaje está desconectado
if character[2] == 1: # Si está conectado
return JsonResponse({'success': False, 'message': '<span class="red-form-response">El personaje debe estar desconectado para ser transferido.</span>'})
# Verificar el token de seguridad
security_token = SecurityToken.objects.filter(user_id=user_id, token=token).first()
if not security_token:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Token de seguridad incorrecto.</span>'})
# Verificar si el token ha expirado
if security_token.expires_at < timezone.now():
return JsonResponse({'success': False, 'message': '<span class="red-form-response">El token ha expirado. Solicite uno nuevo.</span>'})
# Verificar si la cuenta de destino existe
with connections['acore_auth'].cursor() as cursor:
cursor.execute("SELECT id FROM account WHERE username = %s", [destination_account])
destination_account_data = cursor.fetchone()
if not destination_account_data:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">La cuenta de destino no existe.</span>'})
# Verificar restricciones en la cuenta de destino
destination_account_id = destination_account_data[0]
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT account, name, class, level, online
FROM characters
WHERE account = %s
""", [destination_account_id])
destination_characters = cursor.fetchall()
if not any(char[3] >= 55 and char[2] != 6 for char in destination_characters):
return JsonResponse({'success': False, 'message': '<span class="red-form-response">La cuenta destino debe tener al menos un personaje de nivel 55 o superior que no sea Caballero de la Muerte.</span>'})
if any(char[2] == 6 for char in destination_characters):
return JsonResponse({'success': False, 'message': '<span class="red-form-response">La cuenta destino no puede tener un Caballero de la Muerte.</span>'})
# Verificar que ninguna cuenta esté online
for char in destination_characters:
if char[4] == 1:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Todos los personajes de la cuenta destino deben estar desconectados.</span>'})
for char in characters:
if char[2] == 1:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Todos los personajes de la cuenta origen deben estar desconectados.</span>'})
# Crear sesión de pago con Stripe
success_url = request.build_absolute_uri(reverse('transfer-success'))
cancel_url = request.build_absolute_uri(reverse('transfer-cancel'))
stripe_response = create_checkout_session(price, success_url=success_url, cancel_url=cancel_url)
if stripe_response["success"]:
# Guardar los datos de la transferencia en la sesión para usarlos después del pago
request.session['transfer_data'] = {
'character_name': character_name,
'destination_account': destination_account
}
return JsonResponse({
'success': True,
'session_id': stripe_response["session_id"],
'stripe_public_key': settings.STRIPE_PUBLIC_KEY
})
else:
return JsonResponse({'success': False, 'message': f'<span class="red-form-response">Error al iniciar el pago: {stripe_response["error"]}</span>'})
return render(request, 'account/transfer_character.html', {'characters': characters, 'price': price})
def transfer_success_view(request):
transfer_data = request.session.get('transfer_data')
if not transfer_data:
return redirect('transfer-character')
character_name = transfer_data['character_name']
destination_account = transfer_data['destination_account']
# Ejecutar comando SOAP
command = f".char changeaccount {destination_account} {character_name}"
response = execute_soap_command(command)
if response is None or response.strip() == "":
message = f"El personaje {character_name} ha sido transferido a la cuenta {destination_account}."
request.session.pop('transfer_data', None) # Limpiar sesión
return render(request, 'account/transfer_success.html', {'message': message})
else:
return render(request, 'account/transfer_success.html', {'message': f"Error: {response}"})
def transfer_cancel_view(request):
return render(request, 'account/transfer_cancel.html')
def store_novawow_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
categories = StoreCategory.objects.filter(parent_category=None)
items = StoreItem.objects.all()
cart_items = Cart.objects.filter(username=username)
total_price = sum([item.total_price() for item in cart_items])
return render(request, 'account/store_novawow.html', {
'categories': categories,
'items': items,
'cart_items': cart_items,
'total_price': total_price,
})
def add_to_cart(request):
username = request.session.get('username')
if not username:
return redirect('login')
if request.method == 'POST':
item_id = request.POST.get('item_id')
item = StoreItem.objects.get(id=item_id)
Cart.objects.create(username=username, item=item)
return JsonResponse({'success': True, 'message': f'{item.name} añadido al carrito.'})
return JsonResponse({'success': False, 'message': 'Error al añadir al carrito.'})
def remove_from_cart(request):
username = request.session.get('username')
if not username:
return redirect('login')
if request.method == 'POST':
cart_id = request.POST.get('cart_id')
Cart.objects.filter(id=cart_id, username=username).delete()
return JsonResponse({'success': True, 'message': 'Artículo eliminado del carrito.'})
return JsonResponse({'success': False, 'message': 'Error al eliminar del carrito.'})
def checkout_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
cart_items = Cart.objects.filter(username=username)
total_price = sum([item.total_price() for item in cart_items])
success_url = request.build_absolute_uri(reverse('checkout_success'))
cancel_url = request.build_absolute_uri(reverse('checkout_cancel'))
stripe_response = create_checkout_session(total_price, success_url, cancel_url)
if stripe_response["success"]:
return JsonResponse({'success': True, 'session_id': stripe_response["session_id"]})
return JsonResponse({'success': False, 'message': 'Error al procesar el pago.'})
def checkout_success(request):
username = request.session.get('username')
if not username:
return redirect('login')
cart_items = Cart.objects.filter(username=username)
for cart_item in cart_items:
command = f".send item {cart_item.item.item_id} {cart_item.item.name} {username}"
execute_soap_command(command)
cart_item.delete()
return render(request, 'account/checkout_success.html', {'message': 'Compra procesada con éxito.'})
def checkout_cancel(request):
username = request.session.get('username')
if not username:
return redirect('login')
return render(request, 'account/checkout_cancel.html', {'message': 'Compra cancelada.'})
def revive_character_view(request):
username = request.session.get('username')
if not username:
return redirect('login')
# Obtener personajes del usuario desde la base de datos `acore_characters`
with connections['acore_characters'].cursor() as cursor:
cursor.execute("""
SELECT name, online
FROM characters
WHERE account = (
SELECT id
FROM acore_auth.account
WHERE username = %s
)
""", [username])
characters_data = cursor.fetchall()
characters = {row[0]: row[1] for row in characters_data} # Diccionario con nombre y estado de conexión
if request.method == 'POST':
character_name = request.POST.get('character')
# Validar si el personaje fue seleccionado
if not character_name:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">Por favor, seleccione un personaje.</span>'})
# Verificar si el personaje pertenece al usuario
if character_name not in characters:
return JsonResponse({'success': False, 'message': '<span class="red-form-response">No tienes permiso para revivir este personaje.</span>'})
# Verificar si el personaje está desconectado
if characters[character_name] == 1: # Si está conectado
return JsonResponse({'success': False, 'message': '<span class="red-form-response">El personaje debe estar desconectado para ser revivido.</span>'})
# Verificar el historial de uso del comando `revive`
last_revive = ReviveHistory.objects.filter(character_name=character_name).order_by('-used_at').first()
if last_revive and last_revive.used_at > now() - timedelta(hours=12):
return JsonResponse({'success': False, 'message': '<span class="red-form-response">El personaje solo puede revivirse una vez cada 12 horas.</span>'})
# Ejecutar el comando SOAP
command = f".revive {character_name}"
response = execute_soap_command(command)
# Si la respuesta es vacía o None, asumir éxito
if response:
ReviveHistory.objects.create(character_name=character_name, used_at=now())
return JsonResponse({'success': True, 'message': f'<span class="ok-form-response">El personaje {character_name} ha sido revivido con éxito.</span>'})
# Manejar respuesta explícita que no indique éxito
return JsonResponse({'success': False, 'message': f'<span class="red-form-response">Error inesperado: {response}</span>'})
return render(request, 'account/revive_character.html', {'characters': characters.keys()})
def unstuck_character_view(request):
username = request.session.get('username')
if not username:
Binary file not shown.
+4
View File
@@ -135,6 +135,10 @@ TEMPLATES = [
},
]
STRIPE_PUBLIC_KEY = "pk_test_51QQrdMI3Vazamytgfb8046k0AwaRR3Cu8ni80b8iglZMUlUZVJarW1azXGXl3qV5VZtr2S7Xmpgr43Zcg73Pd8eT00C8CPOnja" # Cambia según tu configuración
STRIPE_SECRET_KEY = "sk_test_51QQrdMI3VazamytgcKpxF9cQcUfZYOam8b3IYgpJnpUBdY4xYOorTHRE0AbArfZbRT4nSbY2DEAMEvgxJl6gmgjJ00OaZgiryS"
WSGI_APPLICATION = 'novawow.wsgi.application'