This document assumes that you understand the concepts of object oriented programming and more specifically with C# programming, such as Classes or Objects, Methods, Properties, Events, etc. If not, it will be much harder to follow along.
This tutorial will cover the basics of data Binding in a WPF application. When you are done with this tutorial, you should be able to create a basic WPF-based graphical program that uses Binding. We will cover the different types of data Binding as well as what works and sometimes what doesn’t.
What is data Binding?
The idea of data Binding is to link a variable of any Type (int, string, object, etc…) to a graphical object’s Property that has the same type.
For example, lets say you have a Button object called myButton in your GUI like this: . The words “Click Me!” is a string property in the Button object: myButton.Text.
Imagine you have a string variable called strProperty in some part of your code that on its own has no way to interact with your GUI code. Lets say you want to change the myButton.Text property to match that string variable. Binding allows the button’s text string to always match a string property in some other object not really related to your GUI so if you change strProperty to equal “Enable” your button text will look like . If you then change the strProperty to “Disable” the button text will automatically change to be without out your back end code having to make any interaction with the GUI on its own.
Without Binding, you would have to write code yourself that would interact with the GUI and update the myButton.Text property when ever you update the string in code. In order to do this without Binding, you would also have to intermingle your background code with your GUI code. This can make it difficult to update or modify your GUI because GUI code is strung throughout all parts of your application. You don’t just have to update your GUI, you have to update all your code that interacts with the GUI.
So Binding allows you to have a back end code that is independent of the GUI. This is especially useful when the GUI needs to be updated or improved or when multiple GUIs exists (skins) and you can switch between them.
There are programming styles associated with developing a GUI separate from the back-end. Two of which are Model-View-Control (MVC) or Model-View-ViewModel (MVVM). This tutorial is not going to cover these, however, it is probably wise for you become familiar with these.
However, there is no reason you are limited to Binding to back end code. You can bind to code that is in the WPF GUI and very powerful applications can be written with little to no back end code.
Requirements for data Binding in WPF
In order to using data Binding, you should have the following requirements:
Your project should be a WPF Application, or your project should include a WPF Window or WPF Control.
Objects your elements bind to should implement System.ComponentModel.INotifyPropertyChanged.
The Binding source can also be “any public property, including properties of other controls, common language runtime (CLR) objects, XAML elements, ADO.NET DataSets, XML Fragments, and so forth.” (Reference: http://msdn.microsoft.com/en-us/magazine/cc163299.aspx).
Copyright ® Rhyous.com – Linking to this page is allowed without permission and as many as ten lines of this page can be used along with this link. Any other use of this page is allowed only by permission of Rhyous.com.
How to add a dynamic image and/or a dynamic button to a row using WPFToolKit DataGrid and DataGridTemplateColumns?
To start, I have a WPF project in Visual Studio 2008. I have installed the WPFToolKit and have added a reference to it in my project.
Often you want to display a DataGrid, but you don’t want to simply display it as is, you want to be able to enhance it and add functionality to it, such as adding an image to the start of each row or adding a button on each row.
Ok, so I have a table created using a DataTable that looks as follows:
IntVal
StrVal
0
normal
1
warning
2
error
I am passing this to a WFPToolKit DataGrid.
As I pass this to a Datagrid I want to add two columns:
I want to add an image that is different if it is normal, warning, or error.
I want to add a button only if it is warning or error.
So the visual would look as follows:
Image
IntVal
StrVal
Action
0
normal
1
warning
2
error
Step 1. Install prerequisites: Install Visual Studio 2008, and download and install the WPFToolkit.
You probably already have this done, and there are no steps for provided for these.
Step 2. Create a new WPF project in Visual studio 2008 and design the WPF interface
So once my project was created and the reference to WPFToolKit added, I then changed the XAML on my default Window1 class.
I needed to add a reference to the toolkit here as well.
I needed to add resources for my button.
I needed to add three separate resources for my images.
The data can come from anywhere but for this basic example, I am just statically creating a DataTable in the Constructor. I also added a property for the DataTable and the DataTable.DefaultView.
Data.cs
using System.Data;
namespace DataGridAddButtonAndImageColumns
{
public class Data
{
#region Member Variables
private DataTable mTable;
#endregion
#region Constructors
/*
* The default constructor
*/
public Data()
{
mTable = new DataTable();
mTable.Columns.Add("IntVal", typeof(int));
mTable.Columns.Add("StrVal", typeof(string));
DataRow row0 = mTable.NewRow();
row0["IntVal"] = 0;
row0["StrVal"] = "normal";
mTable.Rows.Add(row0);
DataRow row1 = mTable.NewRow();
row1["IntVal"] = 1;
row1["StrVal"] = "warning";
mTable.Rows.Add(row1);
DataRow row2 = mTable.NewRow();
row2["IntVal"] = 2;
row2["StrVal"] = "error";
mTable.Rows.Add(row2);
}
#endregion
#region Properties
public DataTable Table
{
get { return mTable; }
set { mTable = value; }
}
public DataView View
{
get { return mTable.DefaultView; }
}
#endregion
#region Functions
#endregion
#region Enums
#endregion
}
}
Step 4 – Create a ViewModel that implements INotifyPropertyChanged.
So creating a ViewModel is not exactly required but there really is benefit to the Model-View-ViewModel design pattern, so I will attempt to follow it even though this is a simple example application.
I created a new object called DataViewModel.
I implemented the INotifyPropertyChanged interface (though for this small application it isn’t used, I don’t want to leave it out cause you might need it for your application.)
I changed the constructor to take the Data object I designed in the previous step.
I expose the Table and the Table’s view as properties.
DataViewModel.cs
using System;
using System.ComponentModel;
using System.Data;
namespace DataGridAddButtonAndImageColumns
{
public class DataViewModel : INotifyPropertyChanged
{
#region Member Variables
readonly Data mData;
#endregion
#region Constructors
/*
* The default constructor
*/
public DataViewModel(Data inData)
{
mData = inData;
}
#endregion
#region Properties
public DataView View
{
get { return mData.View; }
}
public DataTable Table
{
get { return mData.Table; }
}
#endregion
#region Functions
#endregion
#region Enums
#endregion
#region INotifyPropertyChanged Members
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void OnPropertyChanged(string propertyName)
{
if (this.PropertyChanged != null)
this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
#endregion
}
}
Step 5 – Add code to pass the DataTable to the DataGrid
So in the Window1.xaml.cs file, I create a new DataViewModel object and pass it a new Data object. I then assign the DataTable to the DataGrid’s DataContext object. My class now looks as follows.
Window1.xaml.cs
using System.Windows;
using System.Windows.Controls;
namespace DataGridAddButtonAndImageColumns
{
/// <summary>
/// Interaction logic for Window1.xaml
/// </summary>
public partial class Window1 : Window
{
#region Member Variables
#endregion
#region Contructor
public Window1()
{
InitializeComponent();
DataViewModel model = new DataViewModel(new Data());
// It is ok to pass either the DataTable or the DataView
// so both lines below work, however I am only using one:
//
// mDataGrid.DataContext = model.View;
// mDataGrid.DataContext = model.Table;
mDataGrid.DataContext = model.Table;
}
#endregion
#region Functions
private void ButtonFixThis_Click(object sender, RoutedEventArgs e)
{
// Do something here
}
#endregion
#region Properties
#endregion
}
}
Now I can compile and run see my simple DataGrid.
IntVal
StrVal
0
normal
1
warning
2
error
Step 6 – Create the DataTemplateSelectors
I am going to use two DataTemplateSelector and I want them to share a base class, so first, I am going to create a base class for them.
I inherit DataTemplateSelector.
I add a function to find the parent Window1 object.
BaseDataTemplateSelector.cs
using System.Windows;
using System.Windows.Controls;
using System.Windows.Media;
namespace DataGridAddButtonAndImageColumns
{
public class BaseDataTemplateSelector : DataTemplateSelector
{
#region Member Variables
#endregion
#region Constructors
/*
* The default constructor
*/
public BaseDataTemplateSelector()
{
}
#endregion
#region Properties
#endregion
#region Functions
protected Window1 GetWindow1(DependencyObject inContainer)
{
DependencyObject c = inContainer;
while (true)
{
DependencyObject p = VisualTreeHelper.GetParent(c);
if (c is Window1)
{
//mSectionControl = c;
return c as Window1;
}
else
{
c = p;
}
}
}
#endregion
}
}
Now I create an ActionDataTemplateSelector and a StatusImageDataTemplateSelector.
The ActionDataTemplateSelector will overload the SelectTemplate function and correctly select the Fix button resource if the status is warning or error.
ActionDataTemplateSelector.cs
using System.Data;
using System.Windows;
namespace DataGridAddButtonAndImageColumns
{
public class ActionDataTemplateSelector : BaseDataTemplateSelector
{
#region Constructors
/*
* The default constructor
*/
public ActionDataTemplateSelector()
{
}
#endregion
#region Functions
public override DataTemplate SelectTemplate(object inItem, DependencyObject inContainer)
{
DataRowView row = inItem as DataRowView;
if (row != null)
{
Window1 w = GetWindow1(inContainer);
if (row.DataView.Table.Columns.Contains("IntVal"))
{
if ((int)row["IntVal"] > 0)
{
return (DataTemplate)w.FindResource("FixThisTemplate");
}
}
return (DataTemplate)w.FindResource("NormalTemplate");
}
return null;
}
#endregion
}
}
The StatusImageDataTemplateSelector also overloads the SelectTempate function and selects the correct image for the status.
StatusImageDataTemplateSelector .cs
using System.Data;
using System.Windows;
namespace DataGridAddButtonAndImageColumns
{
public class StatusImageDataTemplateSelector : BaseDataTemplateSelector
{
#region Constructors
/*
* The default constructor
*/
public StatusImageDataTemplateSelector()
{
}
#endregion
#region Functions
public override DataTemplate SelectTemplate(object inItem, DependencyObject inContainer)
{
DataRowView row = inItem as DataRowView;
if (row != null)
{
if (row.DataView.Table.Columns.Contains("IntVal"))
{
Window1 w = GetWindow1(inContainer);
int status = (int)row["IntVal"];
if (status == 0)
{
return (DataTemplate)w.FindResource("StatusTemplateNormal");
}
if (status == 1)
{
return (DataTemplate)w.FindResource("StatusTemplateWarning");
}
if (status == 2)
{
return (DataTemplate)w.FindResource("StatusTemplateError");
}
}
}
return null;
}
#endregion
}
}
Step 7 – Create functions that add the new columns and have the constructor call each function.
Each function must:
Create a new DataGridTemplateColumn.
Assign a string for the Header.
Create a new DataTemplateSelector and assign it to the DataGridTemplateColumn’s CellTemplateSelector.
Add the new DataGridTemplateColumn to the DataGrid.
public void CreateActionButtonColumn()
{
DataGridTemplateColumn actionColumn = new DataGridTemplateColumn { CanUserReorder = false, Width = 85, CanUserSort = true };
actionColumn.Header = "Action";
actionColumn.CellTemplateSelector = new ActionDataTemplateSelector();
mDataGrid.Columns.Add(actionColumn);
}
public void CreateStatusColumnWithImages()
{
DataGridTemplateColumn statusImageColumn = new DataGridTemplateColumn { CanUserReorder = false, Width = 85, CanUserSort = false };;
statusImageColumn.Header = "Image";
statusImageColumn.CellTemplateSelector = new StatusImageDataTemplateSelector();
mDataGrid.Columns.Insert(0, statusImageColumn);
}
Don’t forget to call the functions in the constructor.
public Window1()
{
InitializeComponent();
DataViewModel model = new DataViewModel(new Data());
// It is ok to pass either the DataTable or the DataView
// so both lines below work, however I am only using one:
//
// mDataGrid.DataContext = model.View;
// mDataGrid.DataContext = model.Table;
mDataGrid.DataContext = model.Table;
CreateActionButtonColumn();
CreateStatusColumnWithImages();
}
Ok, so now you are finished. This should be working for you if you compile and run the program.
Image
IntVal
StrVal
Action
0
normal
1
warning
2
error
Options for handling the images without using a static path
The images were called statically in the above example, however, that will be problematic in actual implementation as each program is installed in a different location and the install location can usually be chosen by a user. You have two options to resolve this, and I will show you how to do both:
Embedding your images
Using image files located in a relative path
Either option work. The second option makes branding a little easier as code doesn’t have to be recompiled with new images to change the images, because the image files can simply be replaced.
Embedding your images
So you can embed your images as resources and use the embedded resources instead. To embed them, do this:
In Visual Studio under your project, create a folder called Images.
Copy your images into that folder.
In the XAML, change each of the image resource lines as shown
Using image files located in a relative path
I decided to NOT embed my images but instead solve this by using a relative path. My preference is for the images to come from actual files in an images directory that is relative to the directory from which the executable is launched:
Make sure to create the Images folder and add the images in the location where you exectuable runs. You may have to add the images folder to both the debug and release directories or otherwise resolve this, else you will get an exception when the images are not found.
Copyright ® Rhyous.com – Linking to this page is allowed without permission and as many as ten lines of this page can be used along with this link. Any other use of this page is allowed only by permission of Rhyous.com.
I have had two Open Source experiences with average non-geeks that I would like to share.
Experience 1 – The in-laws are using Linux
I spent Easter at my in-laws and while I was their I of course took some time to “fix” their computers. Doing some maintenance to their computers is a regular task for me. However, they had recent purchased a new netbook and it was the only computer that they didn’t need me to work on.
“You got a new Netbook?”, I asked in surprise. Not that they consult me before every purchase but I usually hear about it. “Can I see it?” I asked.
My father-in-law, a retired seminary teacher who does real estate on the side, went and got the new little Netbook.
I booted it up and while the average person couldn’t tell it was running Linux, I immediately recognized the KDE interface despite the fact that it was tweaked to look as much like windows as possible.
I pressed “Ctrl + Alt + Backspace and sure enough Xorg restarted.
The Netbook is a pretty cool system. It is featured more like a smart phone than a computer, in that it has a tabbed window and you have a limited amount of icons on each tab, including needed items such as a browser, a documentation suite (Google Docs), etc…
My son’s grandparents are using Linux and they don’t even know it. While my curiosity told me to figure out how to enable the root account and start hacking around, I pushed aside the temptation because it was pleasure enough to know that my predictions are coming true.
I said, “By 2010, Linux will be above the watermark of requirements for the majority of users, and will start taking the market by storm.” And I am telling you it has begun.
Well, you might argue that this one purchase by my grandparents doesn’t mean this is true.
Well, I would retort that it isn’t just this one incident.
Netbooks are very popular and selling fairly well among all walks of life, not just to my grandparents.
There are many Google phones that are running Android, based on the Linux kernel.
Slashdot has a story where Ubuntu is claiming 12 million users and Fedora claims 24 million.
My company, LANDesk, continues to get an increased amount of request to support Linux flavors.
Experience 2 – A friend of a friend needing to compile an open source app on OS X
My favorite Operating System is FreeBSD, which has a great desktop version PC-BSD. While these are not exactly Linux, they are open source and actually more free than Linux (see my post on licenses). The rise in the use of FreeBSD and PC-BSD is also increasing rapidly.
Windows is the most used operating system by far. Did you know that the second most used operating system is FreeBSD-based. Yes, Macintosh users, underneath the hood of your pretty graphical user interface (GUI), you have a system that is derived in a large amount from FreeBSD.
Yes, if you are running OS X, you are running a system that is, underneath the hood, very similar to FreeBSD. It has a nice ports system called MacPorts that is a very similar system to FreeBSD’s ports system.
Well, as a replacement for a Visio diagram, I used the program Dia so that some of my friends could have the ability to modify and change the diagram (which happens about once a quarter) as desired without spending way too much for Visio when they otherwise would never ever use it. Well, a friend of a friend called me and wanted to use it.
Unfortunately at this time, Dia doesn’t have a version for OS X, but can be installed using MacPorts. So I found myself showing the average user how to install MacPorts. Unfortunately, I don’t have a Mac, so I couldn’t write a walk-thru of doing this and I don’t know if the friend of a friend was successful in installing Dia on OS X, but still, this average user wanted to do it and wanted this open source app that was available to him only because his system was derived in large part from FreeBSD.
Ok, so I have an object that is to be compared to a default value and based on the comparison has a status of either normal (0), warning (1), or error (2). Of course, it has an array of child objects that each can also be normal, warning, or error. This parent object should have the status that is the worst or greatest.
So I wrote an object caled StatusHandler.cs that does this in C#. It is simple.
/*Copyright 2010 Jared Barneck All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY Jared Barneck ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
* SHALL <COPYRIGHT HOLDER> OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
* THE POSSIBILITY OF SUCH DAMAGE.
*
* The views and conclusions contained in the software and documentation are those
* of the authors and should not be interpreted as representing official policies,
* either expressed or implied, of Jared Barneck.
*/
namespace StatusHandler
{
/*
* The purpose of this class is to hold the worst result
* received when comparing values in a multicolum row.
*/
public class StatusHandler
{
#region Member Variables
private CompareResult mResult = CompareResult.Normal;
#endregion
#region Constructors
/*
* The default constructor
*/
public StatusHandler()
{
}
public StatusHandler(CompareResult inResult)
{
mResult = inResult;
}
#endregion
#region Properties
public CompareResult Result
{
get { return mResult; }
// Don't allow setting, this should be
// done by the AddResult function;
}
#endregion
#region Functions
/*
*
*/
public void AddResult(CompareResult inResult)
{
// Once an error, always an error
if (Result == CompareResult.Error)
{
return;
}
// If a warning, only change the value
// If the new value is an error.
if (Result == CompareResult.Warning)
{
if (inResult == CompareResult.Error)
{
mResult = inResult;
}
return;
}
// If result is not an error or warning, then
// it is most efficient just to set the new
// value to the incoming value.
mResult = inResult;
}
/*
* Sets the status back to normal
*/
public void Reset()
{
mResult = CompareResult.Normal;
}
#endregion
#region Enums
public enum CompareResult
{
Normal = 0,
Warning,
Error
}
#endregion
}
}
I have a DataColumn that contains an space and I just couldn’t get the DataTable.Select(“Column Name=value) function to work.
So i found a solution on some other guys wordpress blog here.
The answer should be obvious to those who use SQL. In SQL to use a space, it often adds square brackets around the column names. [Column Name]. Yes, using square brackets is the solution.
String colName = "Column Name";
String Value = "some data";
DataTable.Select("[" + colName + "]='" + value + "'");
I was recently made aware of a new distribution of FreeBSD called GhostBSD. One of the focuses of GhostBSD is to provide a FreeBSD-based desktop that uses GNOME.
I’ll be honest, I like KDE over GNOME and probably always will, but my opinion is not your opinion, and I have heard plenty of opinions amongst FreeBSD users that GNOME is preferred by them. So this is going to be a good thing for those of you who prefer GNOME.
They have released their first amd64 version, which I downloaded and installed to my VMWare environment. Here is a screen shot.
I was pleased to find that it was a Live CD, as well, until I realized that it was a Live CD only. There are such a large number of people who have asked about a FreeBSD distro that focus on the desktop using GNOME, that I was actually disappointed to find out that it does not install to the hard drive. However, if this distribution becomes popular, I am sure that the distribution could eventually include an installer.
It downloads and fits on one CD (not DVD) and so the download was rather quick for me.
I installed to my VMWare environment, however, the keyboard didn’t work. Maybe the i386 version would work. It might be worth detecting why this didn’t work and submitting a bug to GhostBSD. It would also be cool if they provided a version that had vmware-tools installed. I am not sure if I could install vmware-tools to a Live CD and if I did, it would probably only be installed until I rebooted.
Great work GhostBSD team. As FreeSBIE is discontinued according to Distrowatch, I will definitely replace my Live CD version of FreeBSD and GhostBSD may be an excellent option.
Here is an article by Simon Mackie that gives 10 Simple Google Search Tricks for those of you who don’t know how to do anything more than type something into Google and click search. With a few more skills, you can get much better search results.
Quote: I’m always amazed that more people don’t know the little tricks you can use to get more out of a simple Google search. Here are 10 of my favorites.
This article is pretty cool in that it reviews the iPad from two angles: from the “techie” angle and from the “non-techie” angle, which is pretty cool. It mentioned that there is a strong polarization to either hate the iPad or be a fan of it.
The haters tend to be techies; the fans tend to be regular people.
Therefore, no single write-up can serve both readerships adequately. There’s but one solution: Write separate reviews for these two audiences.
With job openings scarce for young people, the number of unpaid internships has climbed in recent years, leading federal and state regulators to worry that more employers are illegally using such internships for free labor.
Convinced that many unpaid internships violate minimum wage laws, officials in Oregon, California and other states have begun investigations and fined employers.
…many employers failed to pay even though their internships did not comply with the six federal legal criteria that must be satisfied for internships to be unpaid.
The FreeBSD Copyright is free as in you don’t have to buy a license but you can do pretty much anything. The BSD Copyright is almost the same.
What you can do:
Use it at home for no cost.
Use it at work for no cost.
Use it at work for a publicly accessible server that you make money on for no cost.
Add or change code at no cost.
Distribute the entire source code at no cost.
Distribute the entire source code with your changes at no cost.
Build binaries at no cost.
Distribute binaries with your source at no cost if you also give it away at no cost.
Distribute binaries without also distributing the original source and your changes.
Write code that uses or links to this code and license your new code however you want.
Embed the binaries in software you sell, at no cost, even if you don’t provide the source.
Note: This list was created by me based on my understanding of what people would want to do with the code.
Do I need a lawyer?
No. Basically, there is almost no instance in which you have to pay a fee to anybody to use a FreeBSD Copyrighted or BSD Copyrighted piece of code.
However, while 100% free in cost to use it, it is not 100% free. Notice I italicized the word almost in the above sentence.
For the FreeBSD Copyright, also known as the New BSD Copyright, there are two requirements you must meet.
1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
And for the BSD Copyright, there are four requirements listed, but as mentioned on the BSD Copyright web site, the third requirement is no longer required.
1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
3. All advertising materials mentioning features or use of this software must display the following acknowledgement:
This product includes software developed by the University of California, Berkeley and its contributors.
4. Neither the name of the University nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
So you can do anything you want with FreeBSD licenses and BSD licenses at no dollar cost, but you have to spend some time and resources to make sure you display some text as required.
I guess if you didn’t want to follow the 2 or 4 steps, you could find someone to pay so you didn’t have to, but the steps are so simple I doubt anyone would choose to try to license the software to not have to follow these steps.
The The GNU Public License or GPL is not completely different but yet don’t be fooled. It is not the same and is far more restrictive than most realize. And it is harder to explain or describe, especially since there is GPLv1, GPLv2, GPLv3, and I am not even discussing the LGPL here.
Use it at work for a publicly accessible server that you make money on for no cost.
Add or change code at no cost.
Distribute the entire source code at no cost.
Distribute the entire source code with your changes at no cost.
Build binaries at no cost.
Distribute binaries with your source at no cost if you also give it away at no cost.
Do I need a lawyer?
For home use, no.
For a business, yes.
If you are doing anything NOT on the above list, you probably need to involve a lawyer. If you stick to the above list, then no, you probably don’t need a lawyer. However, the GPL is so long and wordy you may need a lawyer to determine if you need a lawyer.
The Difference between the BSD/FreeBSD Copyrights and the The GNU Public License or GPL
The first noticeable difference is that the FreeBSD Copyright is 25 lines (when wrapped at 78 characters with some lines blank due to section separation) while the GPL is 339 lines (when wrapped at 78 characters with some lines blank due to section separation). So it is much more difficult to learn and understand the GPL and there is a higher likelihood to take a wrong step.
The following items were removed these from the GPL’s can-do list because you can’t do them without permission from the author, which most likely will come at a cost but not always. Sometimes, the author will just say, “Yes, you can use it in your proprietary software” and sometimes they will charge a fee. However, even in those instances you probably need to pay a lawyer to draft and agreement and get it signed. However, one problem with GPL is that there are usually many different authors and so obtaining such permission becomes impossible.
Distribute binaries without also distributing the original source and your changes.
Write code that uses or links to this code and license your new code however you want.
Embed the binaries in software you sell, at no cost, even if you don’t provide the source.
Lets put this in a table:
What you can do?
BSD/FreeBSD Copyright
GNU Public License or GPL
1.
Use it at home for no cost.
x
x
2.
Use it at work for no cost.
x
x
3.
Use it at work for a publicly accessible server than you make money on for no cost.
x
x
4.
Add or change code at no cost.
x
x
5.
Distribute the entire source code at no cost.
x
x
6.
Distribute the entire source code with your changes at no cost.
x
x
7.
Build binaries at no cost.
x
x
8.
Distribute binaries with your source at no cost if you also give it away at no cost.
x
x
9.
(Commercial) Distribute binaries without also distributing the original source and your changes.
x
10.
(Commercial) Write code that uses or links to this code and license your new code however you want.
x
11.
(Commercial) Embed the binaries, without a license fee, in software you sell, even if you don’t provide the source.
x
Conclusion
For use at home or work or school or play
In all practicallity there is no difference to a home user between the BSD/FreeBSD Copyrights and the GPL.
For Free Distribution
There is one slight difference in free distribution. Any code you write that uses GPL code must be GPL too. With the BSD/FreeBSD copyright, that is not the case. If you write software that uses or links to BSD licensed software, you can still choose your own license.
For Commercial and Enterprise Use
This is where the difference mainly resides between these two licenses.
For use internally for an enterprise or any use that doesn’t distribute the code, there is no difference.
However, when it comes to including the code or a binary in software that you sell, you are not free to do so. The BSD/FreeBSD Copyrights are much more business and enterprise friendly.
DISCLAIMER
I am not a lawyer. I am not responsible in any way for the misuse of a license based on this post, even if the post is has some piece of data that is blatantly wrong. It is the responsibility of the user of licensed or copyrighted software to make sure the license agreement or copyright is adhered to properly.
Many of you may not know this but my wife, Michelle, is an Advertising consultant. Since she has done so well branding her blog, www.alittletipsy.com, Google (now Topeka) has hired her to handle their new Topeka brand. She has the daunting task of making the word Topeka as popular as the word Google.
So of course we have to move to Mountain View, California where Google…sorry, Topeka, Inc…has its headquarters. She will work on this new Topeka brand. Her first goal is to get the phrase “I topeka’d him” into the next romantic comedy to leave Hollywood.
I will become a stay-at-home Dad. This will be a great blessing for me. I will be volunteering a few hours a day at the local High School as a consultant for the organization called TWNSS (Teachers With No Social Skills). As a long time geek who has struggled to overcome social skills issues, I can now use my experiences to help others.
It is going to be a big life change.
Please congratulate my wife and I. We will miss our friends in Utah.
K-3D 0.8.0.0 is not yet released but it is now compiling and working on FreeBSD 8…I hope to help update the port as soon as the final source is released.
The developers at K-3D are great. So I have been working with the developers at K-3D to get things working well for FreeBSD 8 on their new version. They have been patient and willing to work with me. There have been some bumps, but it is now working pretty well.
Anybody who is working in 3D animation should check out K-3D. If you are looking for a free 3D animation program, it doesn’t get better. I tried other open source 3D applications and didn’t find them any where near as easy to use nor anywhere near as intuitive. I also have it running on Windows 7.
One of the coolest features about K-3D is the ability to have a scripted tutorial. It is not just a video, it actually moves your mouse and really demonstrates using the application. Go to Help and select Tutorials and choose the “Creating a mug” tutorial and watch it move your mouse and really create a 3D mug.
If you have used or maybe after you read this post you decide to use K-3D, then take a moment and either buy some swag from them or donate a few bucks to them.
So sometimes you have to have a function that can do something to any native type.
Below are two snippets to speed up the coding for you.
Ok, so of course there are times when you can use Generics.
public class myclass<T>
{
myclass(T inT)
{
// your class
}
}
However, there are functions that don’t work with a generic type T.
public class myclass<T>
{
myclass(T inT1, T inT2)
{
if (inT1 < inT2)
{
// do something
}
}
}
[/sourcecode]
This results in an error: Error 1 Operator '<' cannot be applied to operands of type 'T' and 'T'.
Maybe you need to handle all the native data types. So it is annoying to type them in, so I created an iftype snippet.
Create a file called iftype.snippet in this directory: C:\Program Files (x86)\Microsoft Visual Studio 9.0\VC#\Snippets\1033\Visual C#\
Copy in this source and save the file.
[sourcecode language="csharp"]
<?xml version="1.0" encoding="utf-8" ?>
<CodeSnippets xmlns="http://schemas.microsoft.com/VisualStudio/2005/CodeSnippet">
<CodeSnippet Format="1.0.0">
<Header>
<Title>iftype</Title>
<Shortcut>iftype</Shortcut>
<Description>Code snippet for an automatically implemented an 'if' statement for each native type.</Description>
<Author>Jared Barneck</Author>
<SnippetTypes>
<SnippetType>Expansion</SnippetType>
</SnippetTypes>
</Header>
<Snippet>
<Declarations>
<Literal>
<ID>varName</ID>
<ToolTip>Variable name</ToolTip>
<Default>t</Default>
</Literal>
</Declarations>
<Code Language="csharp"><![CDATA[
if ($varName$.Equals(typeof(bool)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(Byte)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(Char)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(DateTime)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(Decimal)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(Double)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(Int16)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(Int32)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(Int64)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(SByte)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(Single)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(String)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(TimeSpan)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(UInt16)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(UInt32)))
{
throw new NotImplementedException();
}
else if ($varName$.Equals(typeof(UInt64)))
{
throw new NotImplementedException();
}
$end$]]>
</Code>
</Snippet>
</CodeSnippet>
</CodeSnippets>
However, you prefer a switch statement to an if statement. Here is the same thing using the switch statement.
Create a file called switchtype.snippet in this directory: C:\Program Files (x86)\Microsoft Visual Studio 9.0\VC#\Snippets\1033\Visual C#\
Copy in this source and save the file.
<?xml version="1.0" encoding="utf-8" ?>
<CodeSnippets xmlns="http://schemas.microsoft.com/VisualStudio/2005/CodeSnippet">
<CodeSnippet Format="1.0.0">
<Header>
<Title>switchtype</Title>
<Shortcut>switchtype</Shortcut>
<Description>Code snippet for an automatically implemented a switch statement for each native type.</Description>
<Author>Jared Barneck</Author>
<SnippetTypes>
<SnippetType>Expansion</SnippetType>
</SnippetTypes>
</Header>
<Snippet>a
<Declarations>
<Literal>
<ID>varName</ID>
<ToolTip>Variable name</ToolTip>
<Default>varName</Default>
</Literal>
</Declarations>
<Code Language="csharp"><![CDATA[
Type t = $varName$;
switch (t.ToString())
{
case "System.Boolean":
throw new NotImplementedException();
break;
case "System.Byte":
throw new NotImplementedException();
break;
case "System.Char":
throw new NotImplementedException();
break;
case "System.DateTime":
throw new NotImplementedException();
break;
case "System.Decimal":
throw new NotImplementedException();
break;
case "System.Double":
throw new NotImplementedException();
break;
case "System.Int16":
throw new NotImplementedException();
break;
case "System.Int32":
throw new NotImplementedException();
break;
case "System.Int64":
throw new NotImplementedException();
break;
case "System.SByte":
throw new NotImplementedException();
break;
case "System.Single":
throw new NotImplementedException();
break;
case "System.String":
throw new NotImplementedException();
break;
case "System.TimeSpan":
throw new NotImplementedException();
break;
case "System.UInt16":
throw new NotImplementedException();
break;
case "System.UInt32":
throw new NotImplementedException();
break;
case "System.UInt64":
throw new NotImplementedException();
break;
}
$end$]]>
</Code>
</Snippet>
</CodeSnippet>
</CodeSnippets>
My source uses subversion and has a .svn directory in each subdirectory, how do I remove those .svn directories?
Method 1 – Exporting with TortoiseSVN
Well, if you are in windows with Tortoise SVN installed, you can right-click on the folder or inside the folder in white space and choose TortoiseSVN | Export. This allows you to select a folder and export your code without the .svn folders.
Method 2 – Scripted deletion
However, if you don’t have a Tortoise SVN Client but you have all those .svn folders, you can easily delete them by a simple one line command from the windows command prompt:
c:\path\to\source> for /F “tokens=*” %A in (‘dir /S /B /AD *.svn’) DO rmdir /S /Q “%A”