Monthly Archives: June 2016

Getting the Angular 2 Router Working for an Office Addin

 

I have simple Angular 2 Office Addin and attempting to use the Angular 2 Router to route between two components. My two components are called ViewOne and ViewTwo.

Here’s what the UI for the Office Addin looks like:

office-addin-angular2-router-pushState-cameron-dwyer-01-addin-ui

When the using the Router to navigate, the following errors related to the this._history.pushState function are thrown to the JavaScript console

office-addin-angular2-router-pushState-cameron-dwyer-02-zone-js-error

The error message text is:

EXCEPTION: Error: Uncaught (in promise): TypeError: this_history.pushState is not a function

The same page displays without any error if it is not running as an Office Addin (rather if I just run the same router code on a standalone web page).

My best guess is that this error is due to the Office Addin framework and the fact that the Angular 2 app is running inside a sandbox iframe. I have tried running the same Angular app in a sandbox iframe on an otherwise generic html page however and I can’t reproduce the error so I think it is unique to something within the Office Addin framework.

This particular error has to do with the Angular 2 app trying to push the URL change to the web browsers history (to support back/forward navigation). In an Office Addin this doesn’t really make much sense as the Addin isn’t in control of the whole page so we wouldn’t want the Addin taking over the browsers URL history anyway.

In order to stop the Angular 2 router trying to make this call to the browser you can use a custom location strategy. In my case I was already using the HashLocationStrategy (rather than the default HTML5 routing strategy).

I went to the Angular 2 GitHub repo and found the source code for the HashLocationStrategy and created a new class in my Angular 2 app called CustomHashLocationStrategy. I just dumped all the source code into the new file, changed the name of the class and removed the two lines of code that try to update the web browsers history as shown below.

office-addin-angular2-router-pushState-cameron-dwyer-03-location-strategy

Now when bootstrapping my Angular 2 app I use my new CustomHashLocationStrategy instead of the HashLocationStrategy. Here’s what that change looks like in code.

Before (click for full size image):

office-addin-angular2-router-pushState-cameron-dwyer-04-bootstrap-before

After (click for full size image):

office-addin-angular2-router-pushState-cameron-dwyer-04b-bootstrap-after

After this change I can now navigate between the 2 routes without any errors being thrown to the console.

office-addin-angular2-router-pushState-cameron-dwyer-05-addin-ui-working

The code shown in this article in the Angular 2 Router in RC1. I also had the same issue using the “Router-Deprecated” in RC1, the same solutions worked for me using the deprecated router.

I also tested that this fix worked across Chrome, IE, Edge and Windows Desktop Office Client.

 

Further reading:

http://stackoverflow.com/questions/36182807/angular-2-routed-apps-hosted-in-iframes

https://www.illucit.com/blog/2016/05/angular2-release-candidate-1-rc1-changes/

https://angular.io/docs/ts/latest/guide/router.html

Solving issues Scaling Remote Desktop on High DPI screens (Surface Pro)

The high density (DPI or Dots Per Inch) of modern screens such as a Surface Pro can cause numerous issues when trying to use Remote Desktop Connection (RDC) to remotely connect to another machine. Add an external monitor to the mix and you’ll be pulling your hair out before long at all.

These are the typical issues you can expect to run into:

  • Can’t get the remote desktop to fill up the entire screen
  • Remote desktop is tiny and you can’t make it any bigger
  • Text and images in remote desktop are really small
  • Mouse cursor in remote desktop is very small or very large
  • Blurry text in remote desktop
  • Blurry images in remote desktop
  • Can’t move remote desktop between screens without issues (e.g. between Surface screen and external monitor)

windows-dpi-scaling-remote-desktop-cameron-dwyer-01-small-remote-desktop

Screenshot (click to enlarge): Remote Desktop Connection on Surface Pro 4, trying to maximize the remote desktop just pushes it to the top right corner of the Surface screen, the icons and text are so small you can hardly read them.

 

windows-dpi-scaling-remote-desktop-cameron-dwyer-2-small-remote-desktop-full-screen

Screenshot (click to enlarge): Remote Desktop Connection on Surface Pro 4, if you try to put the remote desktop into full screen mode, you end up with the same tiny text and images just centred on the Surface screen with a black background around it.

 

windows-dpi-scaling-remote-desktop-cameron-dwyer-03-blurry-text-large-fonts-small-cursor

Screenshot (click to enlarge): Remote Desktop Connection on Surface Pro 4 opened on an external monitor. Trying to show the Remote Desktop on an external monitor is often affected by; Blurry text/images/fonts (such as the Word ribbon), some really oversized text (such as the window title), tiny mouse cursor (or reverse, sometimes I get a massive cursor)

 

Almost all the symptoms above are due to differences in DPI and resolutions between:

  • The host machine
  • The remote machine session
  • The host screen and the external screen

I have transitioned across to using a Surface Pro 4 as my main work machine, I don’t do much development work directly on the Surface, rather I have a few virtual machines running on servers in the office and in Azure. As soon as I tried to RDC to these virtual machines I immediately started running into these problems.

The closest thing I have found to a silver bullet that addresses most of these issues in one hit is to stop using the Remote Desktop Connection client that comes built into Windows 10. Instead I now use a separate free product that Microsoft has available called Remote Desktop Connection Manager.

Remote Desktop Connection Manager has the added benefits of:

  • A navigation list of machines you regularly connect to make it super fast to open and switch between connections
  • Persistence of connection credentials
  • Lots more configuration options (compared to the standard RDC)

windows-dpi-scaling-remote-desktop-cameron-dwyer-04-desktop-connection-manager

Screenshot (click to enlarge): Remote Desktop Connection Manager layout

 

windows-dpi-scaling-remote-desktop-cameron-dwyer-05-remote-desktop-scaled-correctly

Screenshot (click to enlarge): Connecting using Remote Desktop Connection Manager I now get the remote desktop completely filling up my Surface screen, and at a resolution and DPI that is useable. Text, images and cursor all appear crisp and as expected! Extending out to an external monitor is much more successful than with the standard RDC. Again in full screen mode, the remote desktop takes up the entire screen and scaling happens without leaving you with blurry text, images and cursor.

 

windows-dpi-scaling-remote-desktop-cameron-dwyer-06-session-full-screen

Screenshot (click to enlarge): Remote Desktop Connection Manager full screen option is a bit hidden away under the Session menu

 

windows-dpi-scaling-remote-desktop-cameron-dwyer-07-display-options

Screenshot (click to enlarge): Remote Desktop Connection Manager also provides a much richer set of configuration options regarding the display if it doesn’t just work for you immediately as well.

 

One important thing to note is that some scaling of the remote desktop occurs when the remote session is established. This only happens when you disconnect and reconnect. So if you have a session open on one of your screens (e.g. Surface screen) and then move that across to an external monitor it may not fill up the whole external screen when you try to go full screen. If you disconnect and reconnect while on the external monitor you will now be able to go full screen on the external monitor. Remote Desktop Connection Manager has a quick way of doing this (just right-click and select Reconnect server).

 

windows-dpi-scaling-remote-desktop-cameron-dwyer-08-reconnect-session

Screenshot: Reconnect server option

 

The handling of DPI and associated scaling behaviour is different based on the version of the operating system. I have been using Remote Desktop Connection Manager from my Windows 10 Surface Pro 4 connecting to a mix of Windows Server 2012 and Windows 10 virtual machines. You may not have as much success if you add other operating system versions into the mix.

While it’s not perfect (I still find problems now and then and taking screenshot of remote connections usually come out smaller or larger than you would expect), its a lot better than just using the standard remote desktop connection client built into Windows.

 

Further reading:

https://blogs.msdn.microsoft.com/rds/2013/12/16/resolution-and-scaling-level-updates-in-rdp-8-1/

https://blogs.msdn.microsoft.com/rds/2015/06/29/zoom-windows-10-remote-desktop-connections-to-older-versions-of-windows-to-improve-your-experience-on-a-hi-dpi-client-display/

%d bloggers like this: