2009-02-25 3 views
0

Я изучаю ASP.NET 3.5 & C#, используя Visual Studio 2008. Большая часть материала, который я изучаю, - через MSDN. Я пытаюсь разработать веб-страницу, которая позволит пользователю создать персонажа для использования в игре RPG. Пользователь должен иметь возможность выделять атрибуты, покупать предметы и т. Д. Когда пользователь будет выполнен, сайт будет форматировать печатный лист символов с пользовательскими данными.asp.net 3.5 Я «получаю» это?

Теперь я все еще обволакиваю вокруг этого материала и хочу знать, правильно ли я нахожусь на правильном пути - если кто-то захочет посмотреть, что у меня есть, и прокомментировать это было бы замечательно. Меня интересует все, что я делаю неправильно или неэффективно, плохой дизайн, дерьмовый код и способы, которые я могу улучшить. Но в основном, я просто хочу знать, правильно ли я нахожусь на правильном пути и не злоупотреблять технологией.

Ниже приведен код, который у меня есть. Это позволяет пользователю выделять определенное количество очков в 4 балла.

Главная:

<%@ Page Language="C#" 
    AutoEventWireup="true" 
    CodeFile="Default.aspx.cs" 
    Inherits="_Default" 
    enableSessionState="true" 
%> 


<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> 


<html xmlns="http://www.w3.org/1999/xhtml"> 
<head runat="server"> 
    <title>Untitled Page</title> 
</head> 
<body> 
    <form id="form1" runat="server"> 
    <div> 
     <!-- MPCP/Bod/Evasion/Masking/Sensor --> 


     <asp:Label ID="MPCP_Rating" runat="server" Text="" ></asp:Label> 
     <br /> <br /> 
     <asp:Label ID="PersonaPool" runat="server" Text="" ></asp:Label> 
     <br /> <br /> 

     <!-- TODO: Format into table --> 
     Bod: 
     <asp:TextBox ID="Bod" runat="server" ontextchanged="Bod_TextChanged" 
      width="25px">0</asp:TextBox> 
     <asp:Button ID="BodInc" runat="server" Text="+" 
      OnClick="Bod_Inc" /> 
     <asp:Button ID="BodDec" runat="server" Text="-" 
      OnClick="Bod_Dec"/> 
     <br /> <br /> 

     Evasion: 
     <asp:TextBox ID="Evasion" runat="server" ontextchanged="Evasion_TextChanged" 
      width="25px">0</asp:TextBox> 
     <asp:Button ID="EvasionInc" runat="server" Text="+" 
      OnClick="Evasion_Inc" /> 
     <asp:Button ID="EvasionDec" runat="server" Text="-" 
      OnClick="Evasion_Dec" /> 
     <br /> <br /> 

     Masking: 
     <asp:TextBox ID="Masking" runat="server" ontextchanged="Masking_TextChanged" 
      width="25px">0</asp:TextBox> 
     <asp:Button ID="MaskingInc" runat="server" Text="+" 
      OnClick="Masking_Inc" /> 
     <asp:Button ID="MaskingDec" runat="server" Text="-" 
      OnClick="Masking_Dec" /> 
     <br /> <br /> 

     Sensor: 
     <asp:TextBox ID="Sensor" runat="server" ontextchanged="Sensor_TextChanged" 
      width="25px">0</asp:TextBox> 
     <asp:Button ID="SensorInc" runat="server" Text="+" 
      OnClick="Sensor_Inc" /> 
     <asp:Button ID="SensorDec" runat="server" Text="-" 
      OnClick="Sensor_Dec" /> 
     <br /> <br /> 
     <asp:Button ID="Submit" runat="server" Text="Submit" /> 

    </div> 
    </form> 
</body> 
</html> 

Code-Behind:

using System; 
using System.Configuration; 
using System.Data; 
using System.Linq; 
using System.Web; 
using System.Web.Security; 
using System.Web.UI; 
using System.Web.UI.HtmlControls; 
using System.Web.UI.WebControls; 
using System.Web.UI.WebControls.WebParts; 
using System.Xml.Linq; 

public partial class _Default : System.Web.UI.Page 
{ 
    private DeckData deck; 

    public _Default() 
    { 
    } 

    // Page events 
    protected void Page_Load(object sender, EventArgs e) 
    { 
     deck = (DeckData)(System.Web.HttpContext.Current.Session["Deck"]); 
     MPCP_Rating.Text = "MPCP Rating: " + deck.MPCP.ToString(); 
     UpdateAvailPersona(); 
    } 

    protected void Unload(object sender, EventArgs e) 
    { 
    } 

    // Helper functions 
    protected void ChangeAttribute(DeckData.Attributes atr, bool inc) 
    { 
     if (inc == true) 
      deck.IncAttribute(atr); 
     else 
      deck.DecAttribute(atr); 

     UpdateAvailPersona(); 

     switch (atr) 
     { 
      case DeckData.Attributes.Bod: 
       Bod.Text = deck.Bod.ToString(); 
       break; 
      case DeckData.Attributes.Evasion: 
       Evasion.Text = deck.Evasion.ToString(); 
       break; 
      case DeckData.Attributes.Masking: 
       Masking.Text = deck.Masking.ToString(); 
       break; 
      case DeckData.Attributes.Sensor: 
       Sensor.Text = deck.Sensor.ToString(); 
       break; 
     } 
    } 

    protected void UpdateAvailPersona() 
    { 
     PersonaPool.Text = "Persona Pool: " + deck.PersonaMax.ToString() + 
      "/" + (deck.CalculateAvailPersona()).ToString(); 
    } 

    // Control Events 
    protected void Bod_Dec(object sender, EventArgs e) 
    { 
     ChangeAttribute(DeckData.Attributes.Bod, false); 
    } 

    protected void Bod_Inc(object sender, EventArgs e) 
    { 
     ChangeAttribute(DeckData.Attributes.Bod, true); 
    } 

    protected void Evasion_Dec(object sender, EventArgs e) 
    { 
     ChangeAttribute(DeckData.Attributes.Evasion, false); 
    } 

    protected void Evasion_Inc(object sender, EventArgs e) 
    { 
     ChangeAttribute(DeckData.Attributes.Evasion, true); 
    } 

    protected void Masking_Dec(object sender, EventArgs e) 
    { 
     ChangeAttribute(DeckData.Attributes.Masking, false); 
    } 

    protected void Masking_Inc(object sender, EventArgs e) 
    { 
     ChangeAttribute(DeckData.Attributes.Masking, true); 
    } 

    protected void Sensor_Dec(object sender, EventArgs e) 
    { 
     ChangeAttribute(DeckData.Attributes.Sensor, false); 
    } 

    protected void Sensor_Inc(object sender, EventArgs e) 
    { 
     ChangeAttribute(DeckData.Attributes.Sensor, true); 
    } 

App-Data (Только класс DeckData)

using System; 
using System.Data; 
using System.Configuration; 
using System.Linq; 
using System.Web; 
using System.Web.Security; 
using System.Web.UI; 
using System.Web.UI.HtmlControls; 
using System.Web.UI.WebControls; 
using System.Web.UI.WebControls.WebParts; 
using System.Xml.Linq; 

/// <summary> 
/// Store deck related data and provide methods for adjusting deck data 
/// </summary> 
public class DeckData 
{ 
    // Set persona multiplier, determines max persona pool 
    private const uint _PersonaMultiplier = 3; 

    public DeckData(uint MPCP) 
    { 
     _MPCP = MPCP; 
     _Bod = _Evasion = _Masking = _Sensor = 0; 

     CalculateMaxPersona(); 
    } 

    // MPCP/Bod/Evasion/Masking/Sensor 
    public enum Attributes 
    { 
     MPCP, 
     Bod, 
     Evasion, 
     Masking, 
     Sensor 
    } 

    private uint _MPCP; 
    private uint _Bod; 
    private uint _Evasion; 
    private uint _Masking; 
    private uint _Sensor; 

    private uint _PersonaMax; 

    /// <summary> 
    /// Acessor/Modifiers 
    /// </summary> 
    public uint MPCP 
    { 
     get { return _MPCP; } 
     set { _MPCP = value; } 
    } 

    public uint Bod 
    { 
     get { return _Bod; } 
     set { _Bod = value; } 
    } 

    public uint Evasion 
    { 
     get { return _Evasion; } 
     set { _Evasion = value; } 
    } 

    public uint Masking 
    { 
     get { return _Masking; } 
     set { _Masking = value; } 
    } 

    public uint Sensor 
    { 
     get { return _Sensor; } 
     set { _Sensor = value; } 
    } 

    public uint PersonaMax 
    { 
     get { return _PersonaMax; } 
    } 

    /// <summary> 
    /// Calculate available persona. Must be called before changing attribs to ensure 
    /// persona pool remains valid 
    /// </summary> 
    /// <returns></returns> 
    public uint CalculateAvailPersona() 
    { 
     // Total deck attribs 
     uint attrTotal = _Bod + _Evasion + _Masking + _Sensor; 

     return _PersonaMax - attrTotal; 
    } 

    /// <summary> 
    /// Recalculate max persona 
    /// </summary> 
    private uint CalculateMaxPersona() 
    { 
     _PersonaMax = _MPCP * _PersonaMultiplier; 
     return _PersonaMax; 
    } 

    /// <summary> 
    /// Increment attribute by 1 point 
    /// </summary> 
    /// <param name="atr"> 
    /// The attribute to increment 
    /// </param> 
    /// <returns> 
    /// false if no Persona available 
    /// true if attribute successfully incremented 
    /// </returns> 
    public bool DecAttribute(DeckData.Attributes atr) 
    { 
     uint availPersona = CalculateAvailPersona(); 

     if (availPersona == _PersonaMax) 
      return false; 

     switch (atr) 
     { 
      case Attributes.MPCP: 
       break; 
      case Attributes.Bod: 
       if (_Bod > 0)    // Check for underflow 
        _Bod -= 1; 
       break; 
      case Attributes.Evasion: 
       if (_Evasion > 0) 
        _Evasion -= 1; 
       break; 
      case Attributes.Masking: 
       if (_Masking > 0) 
        _Masking -= 1; 
       break; 
      case Attributes.Sensor: 
       if (Sensor > 0) 
        _Sensor -= 1; 
       break; 
     } 

     // Check to see if we updated an attribute using cached persona 
     if(availPersona != CalculateAvailPersona()) 
      return true; 
     return false; 
    } 

    public bool IncAttribute(DeckData.Attributes atr) 
    { 
     uint availPersona = CalculateAvailPersona(); 

     if (availPersona == 0) 
      return false; 

     switch (atr) 
     { 
      case Attributes.MPCP: 
       break; 
      case Attributes.Bod: 
       _Bod += 1; 
       break; 
      case Attributes.Evasion: 
       _Evasion += 1; 
       break; 
      case Attributes.Masking: 
       _Masking += 1; 
       break; 
      case Attributes.Sensor: 
       _Sensor += 1; 
       break; 
     } 

     return true; 
    } 
} 

Спасибо!

ответ

3

Если вы хорошо разбираетесь в html, откажитесь от web-форм и используйте инфраструктуру mvc, например asp.net mvc или fubu mvc.

Если вы плохо разбираетесь в html, изучите html, откажитесь от веб-форм и используйте инфраструктуру mvc.

+1

Я не уверен, что это лучший совет. Веб-формы по-прежнему чрезвычайно распространены. Я не вижу, как MVC проникает через пару лет вниз по линии. Это применимо только к ASP.NET - PHP mvc frameworks везде! –

+0

Прохладный, это очищает некоторые вещи для меня. Я также заинтересован в изучении PHP. Я полагаю, это было бы лучшим местом для начала исследования MVC-фреймворков. – 2009-02-25 12:47:33

+0

Я чувствую, что здесь не следует недооценивать структуру MVC ... Поскольку знания, которые вы можете получить от него, также будут использоваться в других рамках. Если asp.net-mvc никогда не будет проходить через дверь, вы все равно сможете использовать его в других средах MVC. –

1

Я просто быстро посмотрел на ваш код, и одна вещь, которая выпрыгивает, - это количество серверных обратных передач, которые будут задействованы в использовании вашего веб-приложения. Каждое изменение атрибута приведет к тому, что страница будет отправлена ​​обратно на сервер, который, в то время как технически является o.k., не обеспечивает отличную работу пользователя.

Возможно, вам захочется изучить методы, которые позволят пользователю сделать все свои изменения, а затем отправить их вместе (например, с помощью javascript на стороне клиента для поддержания распределения точек атрибутов) или, альтернативно, использовать AJAX для асинхронно отсылать изменения к серверу, что приводит к более плавному пользователю.

EDIT: Используя модель, которую вы используете, вы можете использовать Command Command Command вместо события Click. Это позволит вам назначать значение CommandName и CommandArgument каждой кнопке, которая может быть восстановлена ​​в коде позади. Это позволит вам иметь только один метод событий для каждой кнопки, которая может решить, какой атрибут изменить и как из этих свойств:

<asp:Button ID="BodInc" runat="server" CommandArgument="Increase" 
     CommandName="Bod" oncommand="AttributeButton_Command" Text="+" /> 
<asp:Button ID="BodDec" runat="server" CommandArgument="Increase" 
     CommandName="Bod" oncommand="AttributeButton_Command" Text="-" /> 

код позади:

protected void AttributeButton_Command(object sender, CommandEventArgs e) 
{ 
    string attriubuteName = e.CommandName; 
    string action = e.CommandArgument; 
    // Do stuff 
} 
+0

Отличная идея, спасибо вам большое :) – 2009-02-28 01:00:40

0

Одно из предложений, которые я хотел бы сделать чтобы посмотреть, как использовать javascript для увеличения/уменьшения ваших счетчиков в вашей разметке, а затем обновлять вашу модель, используя значения текстовых полей при отправке формы. Как предлагает @Andy, вы также можете делать обновления через AJAX, чтобы уменьшить видимость пользовательского интерфейса, но, учитывая простые правила, которые у вас есть, я думаю, что делать это на стороне клиента и отправлять сообщения один раз - это путь.

Если вы хотите, чтобы пользователь вводил числовые значения напрямую, я бы пошел на статическое отображение выбранного номера и принудительно использовал кнопки вверх/вниз. Вы можете сделать это похожим на комбинацию , которая разрешает выбор вверх/вниз, если сумма выбранных в данный момент значений меньше доступной суммы. Конечно, вам нужно будет обновить код, чтобы подтвердить, что максимальные значения не превышены. Запрет прямого ввода пользователем избавит вас от необходимости проверки того, что введены только числовые значения.

Bod  + [0] = 
Evasion + [0] - 
Masking + [0] - 
Sensor + [0] - 
Total  0 
Maximum  ? 

Вы также хотите подумать о стилизации с использованием классов CSS, а не указывать ширину непосредственно в вашей разметке. Использование CSS поможет вам сохранять постоянный внешний вид во всем приложении. и позволяют вам быстро и легко изменить этот внешний вид и изменения (по большей части) на ваш CSS, а не на свой код приложения.

Смежные вопросы