Saturday, January 23, 2010

Container.DataItemIndex - Getting GridView's Row Index

Every once in a while you need to get the index of the row in a GridView that triggered an event. You can setup the CommandArgument to store the row’s index for use in your code behind. In the GridView:
<asp:GridView ID="gridView" runat="server" DataKeyNames="myId" OnRowCommand=" gridView_RowCommand">
    <Columns>
        <asp:TemplateField ShowHeader="False">
            <ItemTemplate>
                <asp:Button ID="btnAdd" runat="server" CommandArgument='<%# Container.DataItemIndex %>'
                    CommandName="Add" Text="Add" />
            </ItemTemplate>
        </asp:TemplateField>
    </Columns>
</asp:GridView>
Referencing in the code-behind:
protected void gridView_RowCommand(object sender, GridViewCommandEventArgs e)
{
    if (e.CommandName == "Add")
    {
        int myId = (int)gridView.DataKeys[Convert.ToInt32(e.CommandArgument)].Value;
    }
}

Tuesday, September 29, 2009

Scrollbar on a GridView

An ASP.NET GridView control will keep expanding down the page as more data is added. What if you want to control its height though? You could using Paging. You can also add scrollbars using styles. Here is an example of how you do this:
<div style="width: 200px; height: 100px; overflow: auto">
    <asp:GridView ID="gvGrid" runat="server"/>
</div>

Friday, August 28, 2009

Reading from Isolated Storage

You learned how to write to Isolated Storage in the previous post. Here is how you read from it:
IsolatedStorageFile isf = IsolatedStorageFile.GetUserStoreForAssembly();
IsolatedStorageFileStream stream = new IsolatedStorageFileStream("pref.txt", FileMode.OpenOrCreate, isf);
StreamReader sr = new StreamReader(stream);
SetWidthAndHeight(sr.ReadToEnd());
sr.Close();

Isolated Storage

Isolated Storage - A private file system managed by the .NET Framework.

Why use it?
Isolated Storage provides a safe location, regardless of user access level, to store information that can be isolated by each user on the machine to store such things as user preferences.

How do I use it?
Here's an example where I store the height and width of a window in a text file on closing.
IsolatedStorageFile isf = IsolatedStorageFile.GetUserStoreForAssembly();
IsolatedStorageFileStream stream = new IsolatedStorageFileStream("pref.txt", FileMode.Create, isf);
StreamWriter sw = new StreamWriter(stream);
sw.WriteLine("Width:" + this.Width);
sw.WriteLine("Height:" + this.Height);
sw.Close();

Where did this text file actually get saved?
Well, on my machine (Vista) it went into C:\Users\[User]\AppData\Local\IsolatedStorage and then through 3 more cryptic folder names until it reached the AssemFiles folder where the "pref.txt" file showed up.

The location can change depending on the OS. See here for other OS locations.

More Info: Article: When and when not to use Isolated Storage

Thursday, August 27, 2009

Reading Data from the Configuration (*.config) File

In the previous post I saved data to the config file. Here is an example of how you would read data from the config file:
if (ConfigurationManager.AppSettings["Width"] != null)
{
    this.Width = Convert.ToDouble(ConfigurationManager.AppSettings["Width"]);
}

if (ConfigurationManager.AppSettings["Height"] != null)
{
    this.Height = Convert.ToDouble(ConfigurationManager.AppSettings["Height"]);
}


More Info: MSDN: ConfigurationManager.AppSettings

Saving Data to the Configuration (*.config) File

Sometimes you want to save data to the configuration file so it's available the next time the application runs. An example of this is saving a window's last height and width upon closing. Here's how you do it:
Configuration config = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);

config.AppSettings.Settings.Remove("Width");
config.AppSettings.Settings.Add("Width", this.Width.ToString());
config.AppSettings.Settings.Remove("Height");
config.AppSettings.Settings.Add("Height", this.Height.ToString());

config.Save(ConfigurationSaveMode.Modified);

Mark, why do I have to call the Remove method before adding?

Every time you call the Add method it appends data instead of overwriting it. Without calling the Remove method your configuration file will go from this:
<configuration>
    <appSettings>
        <add key="Width" value="402" />
        <add key="Height" value="177" />
    </appSettings>
</configuration>
to this on the next save:
<configuration>
    <appSettings>
        <add key="Width" value="402,300" />
        <add key="Height" value="177,154" />
    </appSettings>
</configuration>
More Info: MSDN: Configuration Class

Friday, August 7, 2009

Starting another .NET program using the Application Domain Class

The AppDomain class allows you to start another .NET assembly in it's own memory space (separate from your main program's memory space). This is different from executing a process from a thread which is contained in your main program's memory space.
Here's an example of how you can do this with the .NET assembly's path:
AppDomain d = AppDomain.CreateDomain("New Domain");
d.ExecuteAssembly(@"C:\LoginToExternalApp.exe");
You can't call just any exe though. It has to run within the .NET Framework runtime. So something like this won't work:
AppDomain d = AppDomain.CreateDomain("New Domain");
d.ExecuteAssembly(@"C:\Program Files\Adobe\Reader 9.0\Reader\AcroRd32.exe");
Another way to start an app is to create a reference to it and then call ExecuteAssemblyByName.
AppDomain appDomain = AppDomain.CreateDomain("New Domain");
appDomain.ExecuteAssemblyByName("LoginToExternalApp");
The user may manually close the application you start up programmatically. If you need to close it down programmatically though, you can use AppDomain.Unload method:
AppDomain.Unload(d);


More Info: MSDN: AppDomain Class