Binding StickNFind for Xamarin fails to compile - xamarin.ios

I'm trying to make a binding for StickNFind to use in a Xamarin-based project.
The problematic class is LeDeviceManager, it inherits CBCentralManagerDelegate, which is an abstract class and the UpdateState(m) method is not a part of the binding.
Here's the Obj-C header for this class:
interface LeDeviceManager : NSObject <CBCentralManagerDelegate>
#property (nonatomic,strong) NSMutableArray *devList;
#property (nonatomic) CBCentralManager *btmgr;
#property (nonatomic,strong) id <LeDeviceManagerDelegate> delegate;
- (id) initWithSupportedDevices: (NSArray *) devCls delegate: (id <LeDeviceManagerDelegate>) del;
- (void) startScan;
- (void) stopScan;
#end
And this is the binding I've come up with, with Objective Sharpie's heavy assistance:
[Model, BaseType (typeof(CBCentralManagerDelegate))]
public partial interface LeDeviceManager
{
[Export ("devList", ArgumentSemantic.Retain)]
NSMutableArray DevList { get; set; }
[Export ("btmgr")]
CBCentralManager Btmgr { get; set; }
[Export ("delegate", ArgumentSemantic.Retain)]
LeDeviceManagerDelegate Delegate { get; set; }
[Export ("initWithSupportedDevices:delegate:")]
IntPtr Constructor (NSObject[] devCls, LeDeviceManagerDelegate del);
[Export ("startScan")]
void StartScan ();
[Export ("stopScan")]
void StopScan ();
[Export ("UpdatedState")]
[New] // Added as suggested by another SO post, also tried [Abstract]
void UpdatedState(CBCentralManager mgr);
}
And I get this error:
Error CS0533: StickNFind.LeDeviceManager.UpdatedState(MonoTouch.CoreBluetooth.CBCentralManager)' hides inherited abstract memberMonoTouch.CoreBluetooth.CBCentralManagerDelegate.UpdatedState(MonoTouch.CoreBluetooth.CBCentralManager)' (CS0533) (SNF_Binding)
How do I fix this:

Hello can you try this instead?
[Protocol] // Added Protocol attribute
[Model]
[BaseType (typeof(NSObject))] //Changed BaseType to NSObject
public partial interface LeDeviceManager : ICBCentralManagerDelegate
{
[Export ("devList", ArgumentSemantic.Retain)]
NSMutableArray DevList { get; set; }
[Export ("btmgr")]
CBCentralManager Btmgr { get; set; }
[Export ("delegate", ArgumentSemantic.Retain)]
LeDeviceManagerDelegate Delegate { get; set; }
[Export ("initWithSupportedDevices:delegate:")]
IntPtr Constructor (NSObject[] devCls, LeDeviceManagerDelegate del);
[Export ("startScan")]
void StartScan ();
[Export ("stopScan")]
void StopScan ();
[Export ("updatedState")] [New] // Notice I changed UpdatedState to updatedState lowercase u
void UpdatedState(CBCentralManager mgr);
}
I highly recommend reading Binding Protocols section of this doc

Related

How to get values from my injected class in MVC 5

I'm very new in MVC 5 and EF6 and need help please.
I have two classes and one single View, I can get the values of class Person but class Address is always null.
I tried use constructor and Bind in PersonController/Create
My classes:
public partial class Person
{
[Key]
public int PersonID { get; set; }
[Required]
[StringLength(40)]
public string Name { get; set; }
[StringLength(40)]
public string Email { get; set; }
public virtual Address AddressDI { get; set; }
}
public class Address
{
[Key]
public int AddressID { get; set; }
[Required]
public string City { get; set; }
[Required]
public string Street { get; set; }
[Required]
public virtual Person PersonDI { get; set; }
}
Controller
public class ContatoController : Controller
{
private readonly Address _address;
public PersonController()
{
_address = new Address();
}
HttpPost]
ValidateAntiForgeryToken]
public ActionResult Create([Bind(Include = #"Name,Email,AddressID,City,")] Person person, Address address)
{
if (ModelState.IsValid)
{
db.Person.Add(person);
db.SaveChanges();
return RedirectToAction("Index");
}
return View(person);
}
/* Other Actions and stuffs */
}
This is my 3 days pain :(
I don't know what exactly you're trying to achieve here. If you want to post a person class then just post the person:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(Person person)
{
if (ModelState.IsValid)
{
db.Person.Add(person);
db.SaveChanges();
return RedirectToAction("Index");
}
return View(person);
}
and in the view, something like:
#model Partner
#Html.BeginForm("Create","Contato", FormMethod.Post){
#Html.TextboxFor(p => Model.AddressDI.City)
}
Also it is a common practice to send data across controller actions in wrapper classes referred to as viewModels. ViewModels usually contain everything that needs to be posted or displayed at a given moment in the view, as well as potential parameters for the view.
something like:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(ContatoViewModel viewModel)
{
var person = new Person();
person.Name = viewModel.Name;
person.Email = viewModel.Email;
person.AddressDI = viewModel.AddressDI
if (ModelState.IsValid)
{
db.Person.Add(person);
db.SaveChanges();
return RedirectToAction("Index");
}
return View(viewModel);
}
Being honest I can't say more without seeing what you're doing in the view.
More on MVVM pattern: https://msdn.microsoft.com/en-us/library/hh848246.aspx
There are tools available such as Jimmy Bogard's AutoMapper which help with copying the values between the view models and the classes.

Azure Service Bus Queue - Serialization with BrokeredMessage

Trying to submit a queue message with an object in the message body but receiving exception on the following line with BrokeredMessage
QueueClient queueClient = QueueClient.CreateFromConnectionString(_connectionString, _queuePathName);
var data = new ABSurvey
{
name = "somename",
version = 1,
language = "eng",
SelfSurvey = new Survey()
{
SurveyItems = new List<ISurveyItem>() { new SurveyItem(){IsSelected = true, ItemId = 1}},
SurveyPerception = Constants.Perception.Self
},
SelfConcept = new Survey()
{
SurveyItems = new List<ISurveyItem>() { new SurveyItem(){IsSelected = true, ItemId = 1}},
SurveyPerception = Constants.Perception.SelfConcept
}
};
BrokeredMessage message = new BrokeredMessage(data);
queueClient.Send(message);
Exception Message - Type '.Survey' with data contract name 'Survey:http://schemas.datacontract.org/2004/07/namespace' is not expected. Consider using a DataContractResolver or add any types not known statically to the list of known types - for example, by using the KnownTypeAttribute attribute or by adding them to the list of known types passed to DataContractSerializer.
These are the models I have -
[DataContract]
public class ABSurvey
{
[DataMember] public string name;
[DataMember] public int version;
[DataMember] public string language;
[DataMember] public ISurvey SelfSurvey;
[DataMember] public ISurvey SelfConcept;
}
[DataContract]
public class SurveyItem : ISurveyItem
{
[DataMember]
public int ItemId { get; set; }
[DataMember]
public bool IsSelected { get; set; }
public SurveyItem()
{
ItemId = -1;
IsSelected = false;
}
}
[DataContract]
public class Survey : ISurvey
{
[DataMember]
public IList<ISurveyItem> SurveyItems { get; set; }
[DataMember]
public Constants.Perception SurveyPerception { get; set; }
public Survey()
{
SurveyItems = new List<ISurveyItem>();
}
}
public interface ISurvey
{
[DataMember]
IList<ISurveyItem> SurveyItems { get; set; }
[DataMember]
Constants.Perception SurveyPerception { get; set; }
}
public interface ISurveyItem
{
[DataMember]
int ItemId { get; set; }
[DataMember]
bool IsSelected { get; set; }
}
Please help locate the issues.
You are missing [KnownType] attributes on your data contract and that is why your message can't be serialized. Detailed explanation can be found hehe.
Simply add [KnownType] attributes to tell serializer which concrete implementation can be used:
[KnownType(typeof(Survey))]
[DataContract]
public class ABSurvey
{
[DataMember]
public string name;
[DataMember]
public int version;
[DataMember]
public string language;
[DataMember]
public ISurvey SelfSurvey;
[DataMember]
public ISurvey SelfConcept;
}
[KnownType(typeof(SurveyItem))]
[DataContract]
public class Survey : ISurvey
{
[DataMember]
public IList<ISurveyItem> SurveyItems { get; set; }
public Survey()
{
SurveyItems = new List<ISurveyItem>();
}
}

How to use automapper?

I have domain class with following definition
public class Category : EntityBase<int>
{
public string Name { get; set; }
public string Description { get; set; }
}
And this class is inherited from a common abstract class
public abstract class EntityBase<TId>
{
public TId Id { get; set; }
}
And my ServiceModel class for this type is look like
public class CategoryDto
{
public string Name { get; set; }
public string Description { get; set; }
public int CategoryId { get; set; }
}
to convert between object i am using automapper. i configured automapper like this
public class AutoMapperServiceConfigurations
{
public static void Configure()
{
Mapper.Initialize(conf => conf.AddProfile(new CategoryProfile()));
}
}
public class CategoryProfile : Profile
{
protected override void Configure()
{
Mapper.CreateMap<Category,CategoryDto>();
}
}
to convert objects when i used automapper in my code it shows some error, my code is given below
var categoryCollection= _categoryRepository.Get<Category>();
// Mapping section here i got error
var returnCollection =
Mapper.Map<IQueryable<Category>, IQueryable<CategoryDto>> (categoryCollection);
return returnCollection;
and the error is
<Error><Message>An error has occurred.</Message><ExceptionMessage>
Unable to cast object of type
'System.Collections.Generic.List`1[PCD.Service.ServiceModels.CategoryDto]' to type 'System.Linq.IQueryable`1[PCD.Service.ServiceModels.CategoryDto]'.
</ExceptionMessage><ExceptionType>System.InvalidCastException</ExceptionType><StackTrace> at AutoMapper.MappingEngine.Map[TSource,TDestination](TSource source)
at AutoMapper.Mapper.Map[TSource,TDestination](TSource source)
at PCD.Service.Implimentations.CategoryService.Read[T]() in g:\AngularJs Practise\ProofOfConceptDemo.Solution\PCD.Service\Implimentations\CategoryService.cs:line 50
at PCD.WebApi.Controllers.CategoryController.Get() in g:\AngularJs Practise\ProofOfConceptDemo.Solution\PCD.WebApi\Controllers\CategoryController.cs:line 23
at lambda_method(Closure , Object , Object[] )
at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ActionExecutor.<>c__DisplayClass13.<GetExecutor>b__c(Object instance, Object[] methodParameters)
at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ActionExecutor.Execute(Object instance, Object[] arguments)
at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.<>c__DisplayClass5.<ExecuteAsync>b__4()
at System.Threading.Tasks.TaskHelpers.RunSynchronously[TResult](Func`1 func, CancellationToken cancellationToken)</StackTrace></Error>
You will want to use the queryable extensions:
http://docs.automapper.org/en/stable/Queryable-Extensions.html
var categoryCollection = _categoryRepository.Get<Category>();
var returnCollection = categoryCollection.ProjectTo<CategoryDto>();
return returnCollection.ToList();

Implement interface member 'System.Collections.IEnumerable.GetEnumerator()'

In the Demo WCF, I am having an error when try to creat class inherits IList<>
public class Profileview: IList<Profile>
{
public Profile ViewProfile(int accountID)
{
return this.Where(p => p.AccountId == accountID).First();
}
}
this is service
namespace DemoService
{
[ServiceContract]
public interface IProfileService
{
[OperationContract]
Profile ViewProfile(int accountID);
}
[DataContract]
public class Profile
{
[DataMember]
public string FirstName { get; set; }
[DataMember]
public string LastName { get; set; }
[DataMember]
public string Location { get; set; }
[DataMember]
public string Genre { get; set; }
[DataMember]
public int AccountId { get; set; }
}
}
Error 1 'ICService.Profileview' does not implement interface member 'System.Collections.IEnumerable.GetEnumerator()'
Can you tell me how to fix it.
Thanks :)
You are not inheriting from IList<Profile> because it is an interface. You are implementing this interface and as such you need to implement all methods required by that interface - which are quite a lot.
I think you really want to inherit from List<Profile>.

Type does not have a default constructor automapper

I have a problem:
public class TDocumentation
{
public XmlElement Summary { get; set; }
public XmlElement LongDescription { get; set; }
public XmlAttribute[] AnyAttr { get; set; }
}
...and:
public class ProxieTDocumentation
{
public XmlElement Summary { get; set; }
......
}
Mapper.CreateMap<Proxies.TDocumentation, TDocumentation>()
...throws:
----> System.ArgumentException : Type "System.Xml.XmlElement" does not have a default constructor automapper
How I can make a mapping on another?
I resolve thie promleb:
Mapper.CreateMap<XmlElement, XmlElement>().ConvertUsing(item => item != null ? item.Clone() as XmlElement : null);

Resources