bind datagrid to collection of custom objects in silverlight 4 - silverlight-4.0

I have a collection say NotificationHistoryCollection which is a collection of NotificationHistory objects which in turn has NotificationDetails object and collection of NotificationHistoryDetail. How do I bind NotificationDetails to a datagrid and NotificationHistoryDetail collection to another datagrid in silverlight 4.0

This should give you some idea:
public partial class MainPage : UserControl
{
public MainPage()
{
InitializeComponent();
friends.Add(new Friend(){Name = "Pappu",Email = new EmailAddress(){Email = "test#test.com"}});
dgFriends.ItemsSource = Friends;
}
ObservableCollection<Friend> friends = new ObservableCollection<Friend>();
public ObservableCollection<Friend> Friends { get { return friends; } set { friends = value; } }
}
public class Friend
{
public string Name { get; set; }
public string LastName { get; set; }
public EmailAddress Email { get; set; }
}
public class EmailAddress
{
public string Email { get; set; }
}
<data:DataGrid x:Name="dgFriends" AutoGenerateColumns="False">
<data:DataGrid.Columns>
<data:DataGridTextColumn Binding="{Binding Email.Email}" Header="EmailAddress" IsReadOnly="True"></data:DataGridTextColumn>
</data:DataGrid.Columns>
</data:DataGrid>
Result:

Related

How to update an existing entity that has a nested list of entities?

I'm trying to update an entity using entity framework but, everytime I try to do it, it raises an error saying that a nested entity the main class contains cannot be tracked.
These are my classes:
public abstract class BaseEntity
{
public int Id { get; set; }
}
public class Dashboard : BaseEntity
{
public int Order { get; set; }
public string Title { get; set; }
public bool Enabled { get; set; }
public virtual ICollection<Submenu> Submenu { get; set; }
}
public class Submenu : BaseEntity
{
public int Order { get; set; }
public bool Enabled { get; set; }
public string Title { get; set; }
public string Image { get; set; }
public string Descriptions { get; set; }
public virtual ICollection<Action> Actions { get; set; }
public int DashboardId { get; set; }
public virtual Dashboard Dashboard { get; set; }
}
public class Action : BaseEntity
{
public string Type { get; set; }
public string Label { get; set; }
public string Url { get; set; }
public string Extension { get; set; }
public virtual Submenu Submenu { get; set; }
public int SubmenuId { get; set; }
}
The one I am using to update is Dashboard, which contains the rest of the classes.
I'm trying to do it using a generic service layer and a generic repository that are defined this way:
public class GenericService<T> : IGenericService<T> where T : BaseEntity
{
private readonly IBaseRepository<T> baseRepository;
public GenericService(IBaseRepository<T> baseRepository)
{
this.baseRepository = baseRepository;
}
public async Task Update(T entity, T attachedEntity)
{
await baseRepository.Update(entity, attachedEntity);
}
}
public class BaseRepository<T> : IBaseRepository<T> where T : BaseEntity
{
private readonly PortalContext dataContext;
private DbSet<T> DbSet { get; set; }
public BaseRepository(PortalContext context)
{
dataContext = context;
DbSet = dataContext.Set<T>();
}
public async Task Update(T entity, T attachedEntity)
{
dataContext.Entry(attachedEntity).State = EntityState.Detached;
DbSet.Attach(entity);
dataContext.Entry(entity).State = EntityState.Modified;
await dataContext.SaveChangesAsync();
}
}
And, at last but no least, this is the way I am configuring everything at Startup.cs
public void ConfigureServices(IServiceCollection services)
{
services.AddDbContext<PortalContext>(
options => options.UseSqlServer(Configuration.GetConnectionString("PortalContext"))
);
services.AddTransient(typeof(IGenericService<>), typeof(GenericService<>));
services.AddTransient(typeof(IBaseRepository<>), typeof(BaseRepository<>));
services.AddTransient<Func<string, ClaimsPrincipal, IRoleCheck>>((serviceProvider) =>
{
return (controllerName, claimsPrincipal) =>
new RoleCheck(serviceProvider.GetRequiredService<IGenericService<Dossier>>(),
serviceProvider.GetRequiredService<IGenericService<DossierTemplate>>(),
serviceProvider.GetRequiredService<IGenericService<Dashboard>>(),
controllerName, claimsPrincipal);
});
}
What the application first does is calling the RoleCheck class to retrieve and filter the required entities and, after that, the user can update them.
When I call the update function at the controller
public async Task<ActionResult<Dashboard>> Put(int id, [FromBody] Dashboard dashboard)
{
var currentDashboard = await service.Get(id);
if (currentDashboard == null)
{
return NotFound();
}
await service.Update(dashboard, currentDashboard);
return Ok();
}
I always receive the next error at the repository:
error
Is there something I am doing wrong? I have been stuck with this for a week now...
Thanks in advance and sorry for the long text, but I wanted it to be clear.
I could finally solve it by adding .AsNoTracking() at the Get() method of my repository:
public async Task<T> Get(int id, Func<IQueryable<T>, IIncludableQueryable<T, object>> includes)
{
IQueryable <T> query = DbSet.AsNoTracking();
if (includes != null)
{
query = includes(query);
}
return await query.FirstOrDefaultAsync(m => m.Id == id);
}

Automapper multiple source to single target in v8.0

I'm new to the whole Automapper world in .net core 3.1 and was going through the docs and SO, but couldnt' find anything for my use case from their latest version 8.0.
Borrowing from another SO post, how could I do this in the new v8.0 configuration?
public class People {
public string FirstName {get;set;}
public string LastName {get;set;}
}
public class Phone {
public string Number {get;set;}
}
Convert to a PeoplePhoneDto like this:
public class PeoplePhoneDto {
public string FirstName {get;set;}
public string LastName {get;set;}
public string PhoneNumber {get;set;}
}
Would I use still do this?
Mapper.CreateMap<People, PeoplePhoneDto>();
Mapper.CreateMap<Phone, PeoplePhoneDto>()
.ForMember(d => d.PhoneNumber, a => a.MapFrom(s => s.Number));
Here is a working demo like below:
Model:
public class People
{
public string FirstName { get; set; }
public string LastName { get; set; }
}
public class Phone
{
public string Number { get; set; }
}
public class PeoplePhoneDto
{
public string FirstName { get; set; }
public string LastName { get; set; }
public string PhoneNumber { get; set; }
}
AutoMapper profile:
public class AutoMapperProfile : Profile
{
public AutoMapperProfile()
{
CreateMap<People, PeoplePhoneDto>();
CreateMap<Phone, PeoplePhoneDto>()
.ForMember(d => d.PhoneNumber, a => a.MapFrom(s => s.Number));
}
}
Startup.cs:
services.AddAutoMapper(typeof(AutoMapperProfile));
Controller:
public class HomeController : Controller
{
private readonly IMapper _mapper;
public HomeController(IMapper mapper)
{
_mapper = mapper;
}
public IActionResult Index()
{
var people = new People() { FirstName = "aaa", LastName = "bbb" };
var phone = new Phone() { Number = "12345" };
var model = _mapper.Map<PeoplePhoneDto>(people); // map dto1 properties
_mapper.Map(phone, model);
//do your stuff...
return View();
}
}
Result:

How to replace null collections in input model with empty ones in ASP.NET core

I have an input model from body:
public class User
{
public string Name { get; set; }
public List<string> Books { get; set; }
}
When user sends
{
"name": "John",
"books": null
}
I Books property is null, but I want it to be empty list. How to do it once for all the controllers and models?
ASP.NET Core knows how to bind the the parameters to the constructor.
This is not the best approach, but it is the one I decided to go with:
public class User
{
public User(string name, List<string> books)
{
Name = name;
Books = books ?? new List<string>();
}
public string Name { get; set; }
public List<string> Books { get; set; }
}
You can also use private field:
public class User
{
private List<string> _books;
public string Name { get; set; }
public List<string> Books
{
get => _books ?? new List<string>();
set { _books = value; }
}
}

xamarin.forms binding to class property not working

In my XamarinForms project I am trying to bind a label text to a property of a class. when I pass in the object to my view the label is not being populated. can someone see what I am doing wrong?
In my view model I have
class ManagerLevelPageViewModel : INotifyPropertyChanged
{
private UserSelections _MyUserSelections;
public UserSelections MyUserSelections
{
get { return _MyUserSelections; }
set {
_MyUserSelections = value;
NotifyPropertyChanged();
}
}
public ManagerLevelPageViewModel(UserSelections _temp)
{
MyUserSelections = _temp;
MyUserSelections.selectedClientName = _temp.selectedClientName;
//myUserSelections = _myUserSelections;
//SetValues();
}
here is the class
public class UserSelections
{
public int selectedClientId { get; set; }
public string selectedClientName { get; set; }
public string selectedClientShortCode { get; set; }
public decimal selectedClientPL { get; set; }
public string TopdayIdentifier { get; set; }
}
here is the view.cs
ManagerLevelPageViewModel vm;
public ManagerLevelPage (UserSelections _myUserSelections)
{
vm = new ManagerLevelPageViewModel(_myUserSelections);
InitializeComponent ();
BindingContext = vm;
DownloadData();
}
lastly here is the xaml
<Label Text="{Binding MyUserSelections.ClientName}"/>
notify property changed
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged([CallerMemberName] string propertyName = "")
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}

How to bind custom model class in mvc

I am new in MVC. I am working on a project where i have created a model class and also context class which is working good if i view the record in normal view.
but if i try to get the data in group by "Series_Name" and bind it into same model class it gives error. here is my code
Here is Model class and DBContextClass
[Table("tblvideo")]
public class TVSerial
{
[Key]
public Int64 Video_ID { get; set; }
public string Series_Name { get; set; }
public string Season_No { get; set; }
public string Episode_No { get; set; }
public string Episode_Name { get; set; }
public string Time_Duration { get; set; }
public string File_Url_480p { get; set; }
public string File_Url_720p { get; set; }
public string Description { get; set; }
public bool Is_Active { get; set; }
public string Image_Url_Small { get; set; }
public string Image_Url_Big { get; set; }
}
public class TvSerialContext : DbContext
{
public DbSet<TVSerial> TvSerials { get; set; }
}
Here is controller class:
public class TvSerialController : Controller
{
public ActionResult ListAllTvSerial()
{
try
{
TvSerialContext tvContext = new TvSerialContext();
List<TVSerial> tv = tvContext.TvSerials.ToList();
return View(tv);
}
catch (Exception ex)
{
return Content(ex.Message);
}
}
}
Above code works as expected, but if i am doing this :
public ActionResult ListAllSeason(string serial)
{
try
{
TvSerialContext tvContext = new TvSerialContext();
List<TVSerial> tv = tvContext.TvSerials.Where(tvs => tvs.Series_Name == serial).Distinct().ToList();
return View(tv);
}
catch (Exception ex)
{
return Content(ex.Message);
}
}
it return all rows , i just want single row from every series_name and custom field "Series_Name,Season_No,Image_Url_Big"
i don't know how to achieve this.
getting result :
Expected result:-
You could do this by creating a view model and using a .GroupBy() clause
public class TVSerialVM
{
public string SeriesName { get; set; }
public string SeasonNo { get; set; }
public string ImageUrl { get; set; }
}
and the query to project into your view model
List<TVSerialVM> model = tvContext.TvSerials.Where(t => t.Series_Name == serial)
.GroupBy(t => new { t.Series_Name, t.Season_No, t.Image_Url_Big })
.Select(t => new TVSerialVM
{
SeriesName = t.Key.Series_Name,
SeasonNo = t.Key.Season_No,
ImageUrl = t.Key.Image_Url_Big
}).ToList();
Side note: Your duplicating data in the database (the season number and the image url). You should consider moving the image urls to another table with a relationship to the season number.
The reason you are getting multiple values even though you are using distinct is the Distinct method does not know what "equal" is for TVSerial.
You can use Distinct with IEqualityComparer.
https://msdn.microsoft.com/en-us/library/vstudio/bb338049(v=vs.100).aspx
Distinct is not guaranteed to on custom objects it doesn't know what to compare. I have used this SO in the past to make my custom object work with Distinct.
Creating a distinct list of custom type in C#