How can I write (Application.Current as App) in my Silverlight class library? - silverlight

I have few public properties in App.xaml.cs which is in project A and I want to refer them in my project B. However my project A has a reference to project B, so I cannot add again the reference of project A in project B otherwise it will result in cyclic error. So how can I refer those properties in my class library? I don't want to use reflection :).
As a workaround I have stored those properties in one class in project B (so it can be referred in project A as well as project B) and made those properties to be static and all works fine. However I am still curious to know what if I had stored them in App.xaml.cs? Any options available?
Thanks in advance :)

The App class should expose things that are only relevant to the application project. As soon as you realised that you wanted these things accessable in B.dll they became relevant to more than just the application project and therefore no longer belong in the application project.
Adding a class to B.dll that carries these things as static properties could be a reasonable approach. Another common pattern is to have a single Current static property.
public MyClass
{
private static MyClass _current = new MyClass();
public static MyClass Current { get { return _current; } }
public string SomeInstanceValue { get; set; }
}
Both A and B would access things using the pattern var x = MyClass.Current.SomeInstanceValue. The advantage of this approach is that it allows the Current property getter to determine if a "current" instance is available or not.
You might also want to review the documentation on ApplicationLifeTimeObjects.

When A and B both need something, maybe you should put them in a C project (C as in Common) and then refer to C from both A and B.

Related

Handling Kinect in Main Window and passing this reference to UserControls

I have a project in WPF with a lot of UserControls, some user controls uses Kinect KinectColorViewer.xaml
I want to handle the sensor discovering and setup (conect, disconect, etc) in main window and serve it to my UserControls, how is the best way to do it?
Here is the project that explains my question.
If you prefer, here are the github link.
From your example code,
Assuming you want to maintain as much of the already available code from Microsoft, you will want to set up a reference to the KinectSensorManager on initializing your application. My constructor normally looks something like this:
private readonly KinectSensorChooser sensorChooser = new KinectSensorChooser();
public KinectSensorManager KinectSensorManager { get; private set; }
public MainViewModel()
{
// initialize the Kinect sensor manager
KinectSensorManager = new KinectSensorManager();
KinectSensorManager.KinectSensorChanged += this.KinectSensorChanged;
// locate an available sensor
sensorChooser.Start();
// bind chooser's sensor value to the local sensor manager
var kinectSensorBinding = new Binding("Kinect") { Source = this.sensorChooser };
BindingOperations.SetBinding(this.KinectSensorManager, KinectSensorManager.KinectSensorProperty, kinectSensorBinding);
}
The KinectSensorManager is just a helper class. You can rewrite code to easily avoid using it, but it doesn't do anything bad (does a lot of nice stuff for you) so I've just keep using it. Also, since I'm assuming you want to re-use as much code as possible, we want to maintain its usage.
For your control, you can extend KinectControl which will set up a bunch of helpful items for you. So...
public partial class KinectUserControl : KinectControl
{
...
}
This will give your control access to a lot of override-able functions that listen in to various events (like KinectSensorChanged). Check our the KinectColorViewer code and you can see how it overrides this function, which allows it to automatically start displaying new data if you swap Kinects.
When declaring your control in the XAML you can now add a reference to the KinectSensorManager:
<my:KinectUserControl KinectSensorManager="{Binding KinectSensorManager}" />
Because your control now has a KinectSensorManager property, it should pass through to your KinectColorViewer control as well.

Is there a #visibility package concept in PHPDoc / PHPStorm?

I have a domain model written in PHP, and some of my classes (entities inside an aggregate) have public methods, which should never be called from outside the aggregate.
PHP does not have the package visibility concept, so I'm wondering if there is some kind of standardized way to define #package and #visibility package in the docblocks, and to have a static analysis tool that would report violations of the visibility scope.
I'm currently trying out PHPStorm, which I've found very good so far, so I'm wondering if this software has support for this feature; if not, do you know any static code analysis tool that would?
The closest parallel to this line of thinking that I see in PHP's capability is using "protected" scope rather than public for these kinds of methods. Granted, that requires using inheritance to grant access to the protected items. In my years of managing phpDocumentor, I've never encountered anything else that attempts to mimic that kind of "package scope" that I remember from my Java days.
If the entities within your aggregate root should not be modifiable without going through the aggregate root, then the only means you have to control that is making the entity a private or protected member so that all modifications to the entity have to go through the aggregate.
class RootEntity {
private $_otherEntity;
public function DoSomething() {
$this->_otherEntity->DoSomething();
}
public function setOtherEntity( OtherEntity $entity ) {
$this->_otherEntity = $entity;
}
}
Someone can still always do:
$otherEntity = new OtherEntity();
$otherEntity->DoSomethingElse();
$rootEntity->setOtherEntity($otherEntity);
Though, I guess you could use the magic __call() method to prohibit setting of the _otherEntity anywhere except during construction. This falls under total hack category :)
class RootEntity {
private $_otherEntity;
private $_isLoaded = false;
public function __call( $method, $args ) {
$factoryMethod = 'FactoryOnly_'.$method;
if( !$this->_isLoaded && method_exists($this,$factoryMethod) {
call_user_func_array(array($this,$factoryMethod),$args
}
}
public function IsLoaded() {
$this->_isLoaded = true;
}
protected function FactoryOnly_setOtherEntity( OtherEntity $otherEntity ) {
$this->_otherEntity = $otherEntity;
}
}
So, from there, when you build the object, you can call $agg->setOtherEntity($otherEntity) from your factory or repository. Then when you are done building the object, call IsLoaded(). From there, nobody else will be able to introduce a new OtherEntity into the class and will have to use the publicly available methods on your aggregate.
I'm not sure if you can call that a "good" answer, but it's the only thing I could think of to truly limit access to an entity within an aggregate.
[EDIT]: Also, forgot to mention...the closest for documentation is that there is an #internal for phpdoc:
http://www.phpdoc.org/docs/latest/for-users/tags/internal.html
I doubt that it will modify the IDE's code completion, however. Though, you could probably make a public function/property but label it as "#access private" with phpdoc to keep it from being in code completion.
So far, PHPStorm does not seem to provide this feature.

Silverlight App object Does not exist' Error

name 'App' does not exist in the current context.
How that possible?
Have to note my initialization code is different than MainPage() type, as I converted SketchFlow app into production Silverlight. They instruct you to do init code via System.Windows.Controls.Frame():
private void Application_Startup(object sender, StartupEventArgs e)
{
this.RootVisual = new System.Windows.Controls.Frame() { Source = new Uri("/MyAppScreen.xaml", UriKind.Relative) };
}
public static string ValueFromHome =
"A Value on Home page";
the goal was to set up public var inside App object so I can access it from various screens down the road
Accessing Resource data requires calling App object I believe as in below, is that correct? so this won't help me
string color = App.Current.Resources["customColor"].ToString();
If you are just storing strings, look into using Resource files. Then they can be translated if that ever becomes necessary.
EDIT (to explain the resource file usage): To access the resource, first create a .resx file in your project (let's say you name it MainResource.resx), change the access modifier drop down to public, add your string with Name: ValueFromHome and Value: "A Value on Home page".
Then you can get the value by adding a using to the namespace of the resource if needed and calling it directly like so:
string value = MainResource.ValueFromHome;
I'd be wary of static variables hanging around. Maybe you could use a MainViewModel to store that value. If you really need a static variable create a new static class in your project and put your ValueFromHome property in that class. The App probably isn't available since it is a Silverlight construct and not made to be available to all areas.

Error Application cast in WPF

i have 2 projects in my solution (main is A.WPF and secondary is B.WPF)
when i'm trying to access variables inside my App.xaml.cs in B.WPF:
filename = ((App)Application.Current).ErrorLogFileName;
i get the following error:
Unable to cast object of type 'A.App' to type 'B.App'.
i also tried the following:
filename = ((B.App)Application.Current).ErrorLogFileName;
but still the same error...
the definition in B.App is:
private string _errorLogFileName = "error log.xml";
public string ErrorLogFileName
{
get { return _errorLogFileName; }
}
please assist...
Looks like you need to do:
filename = ((A.App)Application.Current).ErrorLogFileName;
The error is saying the type is A.App, yet in both cases you are trying to cast to B.App.
There can only be one current application also.
Application.Current refers to the current application. The only way to be allowed to cast the current App to another App-type is when the other App-type is a base class of the current App-type.
Are A.App and B.App siblings or is B.App a base class of A.App?
If you don't want B to have a reference to A (or can't as you want A to reference B and that would cause a circular reference), then you need a common type defined in a third assembly that both A and B reference. In our implementation we tend to have a ConfigurationData type that is in a separate project referenced by both Wpf projects, e.g.
public static class ConfigurationData
{
private static string _errorLogFileName = "error log.xml";
public string ErrorLogFileName
{
get { return _errorLogFileName; }
}
}
Another approach would be to define an Interface for your ErrorLogFileName property in a 3rd assembly that both A and B reference, and then implement that interface on your Wpf Application class - A and B would then both be able to cast to that type. If you wanted your A project to set the values on that at runtime, you could make the ErrorLogFileName a read-write property instead and initialize it in your application startup.
I personally prefer using a separate ConfigurationData type from the Wpf app object for this kind of stuff (ErrorLogFileName etc.) as it can then also be used for code that might execute in a unit test and therefore might not be running under a Wpf application - it also avoids having to do casts all over the place (ConfigurationData.ErrorLogFileName instead of ((IAppConfigurationData)Application.Current).ErrorLogFileName.
BTW, if you have an Application object in both assemblies it sounds like you might have both assemblies configured to build as Output type: Windows Application in your project properties. You should only really have one assembly that is configured as the Windows Application and the rest should be Class Library to avoid confusing numbers of Application classes being generated - only the one in the main EXE (and it's related resources) will get created at runtime.

Considerations when architecting an extensible application using MEF

I've begun experimenting with dependency injection (in particular, MEF) for one of my projects, which has a number of different extensibility points. I'm starting to get a feel for what I can do with MEF, but I'd like to hear from others who have more experience with the technology. A few specific cases:
My main use case at the moment is exposing various singleton-like services that my extensions make use of. My Framework assembly exposes service interfaces and my Engine assembly contains concrete implementations. This works well, but I may not want to allow all of my extensions to have access to all of my services. Is there a good way within MEF to limit which particular imports I allow a newly instantiated extension to resolve?
This particular application has extension objects that I repeatedly instantiate. I can import multiple types of Controllers and Machines, which are instantiated in different combinations for a Project. I couldn't find a good way to do this with MEF, so I'm doing my own type discovery and instantiation. Is there a good way to do this within MEF or other DI frameworks?
I welcome input on any other things to watch out for or surprising capabilities you've discovered that have changed the way you architect.
Is there a good way within MEF to
limit which particular imports I allow
a newly instantiated extension to
resolve?
Load the extension code in a separate container, and make sure that the restricted parts are not available in that container. Let's simplify the situation to these classes to construct an example:
[Export]
public class MyExtension
{
[Import]
public PublicService Service { get; set; }
}
[Export]
public class PublicService
{
}
[Export]
public class InternalService
{
}
[Export]
public class Program
{
[Import]
public MyExtension Extension { get; set; }
[Import]
public PublicService Service1 { get; set; }
[Import]
public InternalService Service2 { get; set; }
}
The goal is to allow MyExtension to import PublicService, but not InternalService. Internal code like Program should be able to import anything. You can achieve that like this:
var publicCatalog = new TypeCatalog(typeof(PublicService), typeof(MyExtension));
var publicContainer = new CompositionContainer(publicCatalog);
var internalCatalog = new TypeCatalog(typeof(Program), typeof(InternalService));
var internalContainer =
new CompositionContainer(internalCatalog, publicContainer);
var program = internalContainer.GetExport<Program>();
This code will not throw a composition exception. If you now change the import on MyExtension to the forbidden InternalService, you will get a composition exception as desired.
A side effect of this set-up is that PublicService cannot import any private services either, just like MyExtension. This kind of makes sense, because otherwise nothing would stop PublicService from exposing a private service via a property.
I have used TypeCatalog for the example, but in practice you should probably use something like the FilteredCatalog sample.
This particular application has
extension objects that I repeatedly
instantiate. I can import multiple
types of Controllers and Machines,
which are instantiated in different
combinations for a Project. I couldn't
find a good way to do this with MEF,
so I'm doing my own type discovery and
instantiation. Is there a good way to
do this within MEF or other DI
frameworks?
You might just be after the PartCreationPolicy attribute, which controls whether a part is shared (as in, created only once per container) or instantiated multiple times for each import. You can also specify the RequiredCreationPolicy parameter in an import attribute.
If that doesn't solve your problem, take a look at the PartCreator sample in the MEF sources (though note that it will probably soon be renamed to ExportFactory, it already has been in the silverlight edition of MEF).

Resources