I have a Visual Studio Setup Project that creates an MSI to install my application. My application has a shell extension with a icon overlay handler so explorer.exe needs to be restarted in order for the icon overlay handler to start working. I have registered a custom action to run on commit that restarts explorer using the following method:
public static void restartExplorer()
{
//stop the shell
try
{
Process process1 = new Process();
ProcessStartInfo startInfo = new ProcessStartInfo();
startInfo.WindowStyle = ProcessWindowStyle.Hidden;
startInfo.FileName = "CMD.exe";
startInfo.Arguments = "/C \"taskkill /f /im explorer.exe\"";
process1.StartInfo = startInfo;
process1.Start();
do
{
Thread.Sleep(100);
if (process1.HasExited)
{
break;
}
} while (true);
}
catch (Exception e)
{
Log.Error("restart explorer", e.StackTrace);
}
//restart the shell
string explorer = string.Format("{0}\\{1}", Environment.GetEnvironmentVariable("WINDIR"), "explorer.exe");
Process process = new Process();
process.StartInfo.FileName = explorer;
process.StartInfo.UseShellExecute = true;
process.Start();
}
This method works well when I test it from visual studio and call it from command line but when it is called from the MSI during install or uninstall it stops explorer, but does not restart it.
Does anyone know why it would work in all circumstances except when called by the MSI during install or uninstall?
Does anyone have an alternate way to restart the explorer from an MSI during install/uninstall?
I have honestly never had the chance to test this out, but here is a quick read: Registering Shell Extension Handlers. Essentially: you are to call SHChangeNotify specifying the SHCNE_ASSOCCHANGED event. If you do not call SHChangeNotify, the change might not be recognized until the system is rebooted.
Found this on github.com: RgssDecrypter - ShellExtension.cs. And another sample.
Killing the explorer is a bit rough... I suggest you use the Restart Manager API for that. The benefit is Explorer knows how to restart itself, and it will restore all opened windows after the restart. Here is a C# utility class that will do it for you. Just call this in you custom action:
...
var rm = new RestartManager();
rm.RestartExplorerProcesses();
...
/// <summary>
/// A utility class to restart programs the most gracefully possible. Wraps Windows <see href="https://msdn.microsoft.com/en-us/library/windows/desktop/cc948910.aspx">Restart Manager API</see>. This class cannot be inherited.
/// </summary>
public sealed class RestartManager
{
/// <summary>
/// The default kill timeout value (2000).
/// </summary>
public const int DefaultKillTimeout = 2000;
/// <summary>
/// The default retry count value (10).
/// </summary>
public const int DefaultRetryCount = 10;
/// <summary>
/// The default retry timeout value (100).
/// </summary>
public const int DefaultRetryTimeout = 100;
/// <summary>
/// Initializes a new instance of the <see cref="RestartManager"/> class.
/// </summary>
public RestartManager()
{
KillTimeout = DefaultKillTimeout;
RetryCount = DefaultRetryCount;
RetryTimeout = DefaultRetryTimeout;
}
/// <summary>
/// Gets or sets the kill timeout in ms.
/// </summary>
/// <value>The kill timeout.</value>
public int KillTimeout { get; set; }
/// <summary>
/// Gets or sets the retry count.
/// </summary>
/// <value>The retry count.</value>
public int RetryCount { get; set; }
/// <summary>
/// Gets or sets the retry timeout in ms.
/// </summary>
/// <value>The retry timeout.</value>
public int RetryTimeout { get; set; }
/// <summary>
/// Restarts the Windows Explorer processes.
/// </summary>
/// <param name="stoppedAction">The stopped action.</param>
public void RestartExplorerProcesses() => RestartExplorerProcesses(null, false, out var error);
/// <summary>
/// Restarts the Windows Explorer processes.
/// </summary>
/// <param name="stoppedAction">The stopped action.</param>
public void RestartExplorerProcesses(ContextCallback stoppedAction) => RestartExplorerProcesses(stoppedAction, false, out var error);
/// <summary>
/// Restarts the Windows Explorer processes.
/// </summary>
/// <param name="stoppedAction">The stopped action.</param>
/// <param name="throwOnError">if set to <c>true</c> errors may be throw in case of Windows Restart Manager errors.</param>
public void RestartExplorerProcesses(ContextCallback stoppedAction, bool throwOnError) => RestartExplorerProcesses(stoppedAction, throwOnError, out var error);
/// <summary>
/// Restarts the Windows Explorer processes.
/// </summary>
/// <param name="stoppedAction">The stopped action.</param>
/// <param name="throwOnError">if set to <c>true</c> errors may be throw in case of Windows Restart Manager errors.</param>
/// <param name="error">The error, if any.</param>
public void RestartExplorerProcesses(ContextCallback stoppedAction, bool throwOnError, out Exception error)
{
var explorers = Process.GetProcessesByName("explorer").Where(p => IsExplorer(p)).ToArray();
Restart(explorers, stoppedAction, throwOnError, out error);
}
/// <summary>
/// Restarts the processes locking a specific file.
/// </summary>
/// <param name="path">The file path.</param>
/// <param name="stoppedAction">The stopped action.</param>
/// <param name="throwOnError">if set to <c>true</c> errors may be throw in case of Windows Restart Manager errors.</param>
/// <param name="error">The error, if any.</param>
/// <exception cref="ArgumentNullException">path is null.</exception>
public void RestartProcessesLockingFile(string path, ContextCallback stoppedAction, bool throwOnError, out Exception error)
{
if (path == null)
throw new ArgumentNullException(nameof(path));
var lockers = GetLockingProcesses(path, false, throwOnError, out error);
if (error != null)
return;
Restart(lockers, stoppedAction, throwOnError, out error);
}
/// <summary>
/// Restarts the Windows Explorer processes locking a specific file.
/// </summary>
/// <param name="path">The file path.</param>
/// <param name="stoppedAction">The stopped action.</param>
/// <param name="throwOnError">if set to <c>true</c> errors may be throw in case of Windows Restart Manager errors.</param>
/// <param name="error">The error, if any.</param>
/// <exception cref="ArgumentNullException">path is null.</exception>
public void RestartExplorerProcessesLockingFile(string path, ContextCallback stoppedAction, bool throwOnError, out Exception error)
{
if (path == null)
throw new ArgumentNullException(nameof(path));
var processes = GetLockingProcesses(path, false, throwOnError, out error);
if (error != null)
return;
var explorers = processes.Where(p => IsExplorer(p)).ToArray();
Restart(explorers, stoppedAction, throwOnError, out error);
}
/// <summary>
/// Determines whether the specified process is Windows Explorer.
/// </summary>
/// <param name="process">The process.</param>
/// <returns><c>true</c> if the specified process is Windows Explorer; otherwise, <c>false</c>.</returns>
public static bool IsExplorer(Process process)
{
if (process == null)
return false;
string explorerPath = Path.Combine(Environment.GetEnvironmentVariable("windir"), "explorer.exe");
return string.Compare(process.MainModule.FileName, explorerPath, StringComparison.OrdinalIgnoreCase) == 0;
}
/// <summary>
/// Gets a list of processes locking a specific file.
/// </summary>
/// <param name="filePath">The file path.</param>
/// <param name="onlyRestartable">if set to <c>true</c> list only restartable processes.</param>
/// <param name="throwOnError">if set to <c>true</c> errors may be throw in case of Windows Restart Manager errors.</param>
/// <param name="error">The error, if any.</param>
/// <returns>A list of processes.</returns>
/// <exception cref="ArgumentNullException">filePath is null.</exception>
public IReadOnlyList<Process> GetLockingProcesses(string filePath, bool onlyRestartable, bool throwOnError, out Exception error)
{
if (filePath == null)
throw new ArgumentNullException(nameof(filePath));
return GetLockingProcesses(new[] { filePath }, onlyRestartable, throwOnError, out error);
}
// NOTE: file name comparison seems to be case insensitive
/// <summary>
/// Gets a list of processes locking a list of specific files.
/// </summary>
/// <param name="filePaths">The files paths.</param>
/// <param name="onlyRestartable">if set to <c>true</c> list only restartable processes.</param>
/// <param name="throwOnError">if set to <c>true</c> errors may be throw in case of Windows Restart Manager errors.</param>
/// <param name="error">The error, if any.</param>
/// <returns>A list of processes.</returns>
/// <exception cref="ArgumentNullException">filePaths is null.</exception>
public IReadOnlyList<Process> GetLockingProcesses(IEnumerable<string> filePaths, bool onlyRestartable, bool throwOnError, out Exception error)
{
if (filePaths == null)
throw new ArgumentNullException(nameof(filePaths));
var processes = new List<Process>();
var paths = new List<string>(filePaths);
var s = new StringBuilder(256);
int hr = RmStartSession(out int session, 0, s);
if (hr != 0)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return processes;
}
try
{
hr = RmRegisterResources(session, paths.Count, paths.ToArray(), 0, null, 0, null);
if (hr != 0)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return processes;
}
int procInfo = 0;
int rebootReasons = RmRebootReasonNone;
hr = RmGetList(session, out int procInfoNeeded, ref procInfo, null, ref rebootReasons);
if (hr == 0)
{
error = null;
return processes;
}
if (hr != ERROR_MORE_DATA)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return processes;
}
var processInfo = new RM_PROCESS_INFO[procInfoNeeded];
procInfo = processInfo.Length;
hr = RmGetList(session, out procInfoNeeded, ref procInfo, processInfo, ref rebootReasons);
if (hr != 0)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return processes;
}
for (int i = 0; i < procInfo; i++)
{
try
{
if (processInfo[i].bRestartable || !onlyRestartable)
{
var process = Process.GetProcessById(processInfo[i].Process.dwProcessId);
if (process != null)
{
processes.Add(process);
}
}
}
catch (Exception e)
{
error = e;
// do nothing, fail silently
return processes;
}
}
error = null;
return processes;
}
finally
{
RmEndSession(session);
}
}
/// <summary>
/// Restarts the specified processes.
/// </summary>
/// <param name="processes">The processes.</param>
/// <param name="stoppedAction">The stopped action.</param>
/// <param name="throwOnError">if set to <c>true</c> errors may be throw in case of Windows Restart Manager errors.</param>
/// <param name="error">The error, if any.</param>
/// <exception cref="ArgumentNullException">processes is null.</exception>
public void Restart(IEnumerable<Process> processes, ContextCallback stoppedAction, bool throwOnError, out Exception error)
{
if (processes == null)
throw new ArgumentNullException(nameof(processes));
if (processes.Count() == 0)
{
error = null;
return;
}
var s = new StringBuilder(256);
int hr = RmStartSession(out int session, 0, s);
if (hr != 0)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return;
}
try
{
var list = new List<RM_UNIQUE_PROCESS>();
foreach (var process in processes)
{
var p = new RM_UNIQUE_PROCESS()
{
dwProcessId = process.Id
};
long l = process.StartTime.ToFileTime();
p.ProcessStartTime.dwHighDateTime = (int)(l >> 32);
p.ProcessStartTime.dwLowDateTime = (int)(l & 0xFFFFFFFF);
list.Add(p);
}
hr = RmRegisterResources(session, 0, null, list.Count, list.ToArray(), 0, null);
if (hr != 0)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return;
}
int procInfo = 0;
int rebootReasons = RmRebootReasonNone;
hr = RmGetList(session, out int procInfoNeeded, ref procInfo, null, ref rebootReasons);
if (hr == 0)
{
error = null;
return;
}
if (hr != ERROR_MORE_DATA)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return;
}
var processInfo = new RM_PROCESS_INFO[procInfoNeeded];
procInfo = processInfo.Length;
hr = RmGetList(session, out procInfoNeeded, ref procInfo, processInfo, ref rebootReasons);
if (hr != 0)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return;
}
if (procInfo == 0)
{
error = null;
return;
}
bool hasError = false;
int wtk = GetWaitToKillTimeout();
var sw = new Stopwatch();
sw.Start();
bool finished = false;
var timer = new Timer((state) =>
{
if (!finished)
{
HardKill(processes);
}
}, null, wtk + 2000, Timeout.Infinite);
hr = RmShutdown(session, RmForceShutdown, percent =>
{
// add progress info code if needed
});
sw.Stop();
if (hr != 0)
{
if (!IsNonFatalError(hr))
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return;
}
hasError = true;
}
if (hasError)
{
HardKill(processes);
}
if (stoppedAction != null)
{
int retry = RetryCount;
while (retry > 0)
{
try
{
stoppedAction(session);
break;
}
catch
{
retry--;
Thread.Sleep(RetryTimeout);
}
}
}
hr = RmRestart(session, 0, percent2 =>
{
// add progress info code if needed
});
if (hr != 0)
{
error = new Win32Exception(hr);
if (throwOnError)
throw error;
return;
}
}
finally
{
RmEndSession(session);
}
error = null;
}
private void HardKill(IEnumerable<Process> processes)
{
// need a hard restart
foreach (var process in processes)
{
try
{
process.Refresh();
if (!process.HasExited)
{
process.Kill();
}
}
catch
{
// do nothing
}
}
Thread.Sleep(KillTimeout);
}
private static bool IsNonFatalError(int hr) => hr == ERROR_FAIL_NOACTION_REBOOT || hr == ERROR_FAIL_SHUTDOWN || hr == ERROR_SEM_TIMEOUT || hr == ERROR_CANCELLED;
/// <summary>
/// Gets the root Windows Explorer process.
/// </summary>
/// <returns>An instance of the Process type or null.</returns>
public static Process GetRootExplorerProcess()
{
Process oldest = null;
foreach (var process in EnumExplorerProcesses())
{
if (oldest == null || process.StartTime < oldest.StartTime)
{
oldest = process;
}
}
return oldest;
}
/// <summary>
/// Enumerates Windows Explorer processes.
/// </summary>
/// <returns>A list of Windows Explorer processes.</returns>
public static IEnumerable<Process> EnumExplorerProcesses()
{
string explorerPath = Path.Combine(Environment.GetEnvironmentVariable("windir"), "explorer.exe");
foreach (var process in Process.GetProcessesByName("explorer"))
{
if (string.Compare(process.MainModule.FileName, explorerPath, StringComparison.OrdinalIgnoreCase) == 0)
yield return process;
}
}
/// <summary>
/// Enumerates a specific process' windows.
/// </summary>
/// <param name="process">The process.</param>
/// <returns>A list of windows handles.</returns>
/// <exception cref="ArgumentNullException">process is null.</exception>
public static IReadOnlyList<IntPtr> EnumProcessWindows(Process process)
{
if (process == null)
throw new ArgumentNullException(nameof(process));
var handles = new List<IntPtr>();
EnumWindows((h, p) =>
{
GetWindowThreadProcessId(h, out int processId);
if (processId == process.Id)
{
handles.Add(h);
}
return true;
}, IntPtr.Zero);
return handles;
}
// https://technet.microsoft.com/en-us/library/cc976045.aspx
/// <summary>
/// Gets the wait to kill timeout, that is, how long the system waits for services to stop after notifying the service that the system is shutting down
/// </summary>
/// <returns>A number of milliseconds.</returns>
public static int GetWaitToKillTimeout()
{
using (var key = Registry.LocalMachine.OpenSubKey(#"SYSTEM\CurrentControlSet\Control", false))
{
if (key != null)
{
var v = key.GetValue("WaitToKillServiceTimeout", 0);
if (v != null && int.TryParse(v.ToString(), out int i))
return i;
}
return 0;
}
}
[DllImport("user32.dll")]
private static extern int GetWindowThreadProcessId(IntPtr handle, out int processId);
private delegate bool EnumWindowsProc(IntPtr hWnd, IntPtr lParam);
[DllImport("user32.dll")]
private static extern bool EnumWindows(EnumWindowsProc callback, IntPtr extraData);
[DllImport("rstrtmgr.dll", CharSet = CharSet.Unicode)]
private static extern int RmStartSession(out int pSessionHandle, int dwSessionFlags, StringBuilder strSessionKey);
[DllImport("rstrtmgr.dll")]
private static extern int RmEndSession(int pSessionHandle);
[DllImport("rstrtmgr.dll", CharSet = CharSet.Unicode)]
private static extern int RmRegisterResources(int pSessionHandle, int nFiles, string[] rgsFilenames, int nApplications, RM_UNIQUE_PROCESS[] rgApplications, int nServices, string[] rgsServiceNames);
[DllImport("rstrtmgr.dll")]
private static extern int RmGetList(int dwSessionHandle, out int pnProcInfoNeeded, ref int pnProcInfo, [In, Out] RM_PROCESS_INFO[] rgAffectedApps, ref int lpdwRebootReasons);
[DllImport("rstrtmgr.dll")]
private static extern int RmShutdown(int dwSessionHandle, int lActionFlags, StatusHandler fnStatus);
[DllImport("rstrtmgr.dll")]
private static extern int RmRestart(int dwSessionHandle, int dwRestartFlags, StatusHandler fnStatus);
/// <summary>
/// Represents the method that handles status updates.
/// </summary>
/// <param name="percentComplete">The percentage completed.</param>
public delegate void StatusHandler(int percentComplete);
private const int RmRebootReasonNone = 0;
private const int RmForceShutdown = 1;
private const int RmShutdownOnlyRegistered = 0x10;
private const int ERROR_MORE_DATA = 234;
private const int ERROR_FAIL_NOACTION_REBOOT = 350;
private const int ERROR_FAIL_SHUTDOWN = 351;
private const int ERROR_SEM_TIMEOUT = 121;
private const int ERROR_CANCELLED = 1223;
private const int CCH_RM_MAX_APP_NAME = 255;
private const int CCH_RM_MAX_SVC_NAME = 63;
[StructLayout(LayoutKind.Sequential)]
private struct RM_UNIQUE_PROCESS
{
public int dwProcessId;
public System.Runtime.InteropServices.ComTypes.FILETIME ProcessStartTime;
}
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
private struct RM_PROCESS_INFO
{
public RM_UNIQUE_PROCESS Process;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = CCH_RM_MAX_APP_NAME + 1)]
public string strAppName;
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = CCH_RM_MAX_SVC_NAME + 1)]
public string strServiceShortName;
public RM_APP_TYPE ApplicationType;
public RM_APP_STATUS AppStatus;
public int TSSessionId;
[MarshalAs(UnmanagedType.Bool)]
public bool bRestartable;
}
[Flags]
private enum RM_APP_STATUS
{
RmStatusUnknown = 0x0,
RmStatusRunning = 0x1,
RmStatusStopped = 0x2,
RmStatusStoppedOther = 0x4,
RmStatusRestarted = 0x8,
RmStatusErrorOnStop = 0x10,
RmStatusErrorOnRestart = 0x20,
RmStatusShutdownMasked = 0x40,
RmStatusRestartMasked = 0x80
}
private enum RM_APP_TYPE
{
RmUnknownApp = 0,
RmMainWindow = 1,
RmOtherWindow = 2,
RmService = 3,
RmExplorer = 4,
RmConsole = 5,
RmCritical = 1000
}
}
Change your command to
cmd /c taskkill /f /im explorer.exe && start explorer.exe || start explorer.exe
and you will find that explorer.exe stops and restarts
I Have An Entry In One Page in my xamarin.forms application that doesn't work properly on my tablet.when I Click on it keyboard appears and I can type in but nothing but placeholder display. this application is work on other android Devices but my tablet not display input data.
tablet : galaxy tab s - android 5.0
phone : galaxy s6 - android 6.0
<ContentPage
xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="MyProject.MyPage"
Title="SomeTitle"
Padding="10, 40, 10, 10">
<Entry Placeholder="Hi"/>
</ContentPage>
In some samsung devices this happens for that you need to write custom renderer and try set text color or backgroundcolor then it should work.
OR
try XLabs Extended Entry
Try this
Usage :
ExtendedEntry entry = new ExtendedEntry
{
Text = "Dummy Text",
TextColor = Color.Black,
PlaceholderTextColor = Color.Black,
};
PCL Code
using Xamarin.Forms;
namespace VHS.MobileApp.eVita.CustomViews
{
public class ExtendedEntry : Entry
{
/// <summary>
/// The font property
/// </summary>
public static readonly BindableProperty FontProperty =
BindableProperty.Create("Font", typeof(Font), typeof(ExtendedEntry), new Font());
/// <summary>
/// The XAlign property
/// </summary>
public static readonly BindableProperty XAlignProperty =
BindableProperty.Create("XAlign", typeof(TextAlignment), typeof(ExtendedEntry),
TextAlignment.Start);
/// <summary>
/// The HasBorder property
/// </summary>
public static readonly BindableProperty HasBorderProperty =
BindableProperty.Create("HasBorder", typeof(bool), typeof(ExtendedEntry), true);
/// <summary>
/// The PlaceholderTextColor property
/// </summary>
public static readonly BindableProperty PlaceholderTextColorProperty =
BindableProperty.Create("PlaceholderTextColor", typeof(Color), typeof(ExtendedEntry), Color.Default);
/// <summary>
/// The MaxLength property
/// </summary>
public static readonly BindableProperty MaxLengthProperty =
BindableProperty.Create("MaxLength", typeof(int), typeof(ExtendedEntry), int.MaxValue);
/// <summary>
/// Gets or sets the MaxLength
/// </summary>
public int MaxLength
{
get { return (int)this.GetValue(MaxLengthProperty); }
set { this.SetValue(MaxLengthProperty, value); }
}
/// <summary>
/// Gets or sets the Font
/// </summary>
public Font Font
{
get { return (Font)GetValue(FontProperty); }
set { SetValue(FontProperty, value); }
}
/// <summary>
/// Gets or sets the X alignment of the text
/// </summary>
public TextAlignment XAlign
{
get { return (TextAlignment)GetValue(XAlignProperty); }
set { SetValue(XAlignProperty, value); }
}
/// <summary>
/// Gets or sets if the border should be shown or not
/// </summary>
public bool HasBorder
{
get { return (bool)GetValue(HasBorderProperty); }
set { SetValue(HasBorderProperty, value); }
}
/// <summary>
/// Sets color for placeholder text
/// </summary>
public Color PlaceholderTextColor
{
get { return (Color)GetValue(PlaceholderTextColorProperty); }
set { SetValue(PlaceholderTextColorProperty, value); }
}
public static readonly BindableProperty BorderRadiusProperty =
BindableProperty.Create<ExtendedEntry, float>(p => p.BorderRadius, default(float));
public float BorderRadius
{
get { return (float)GetValue(BorderRadiusProperty); }
set { SetValue(BorderRadiusProperty, value); }
}
}
}
Droid Code :
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Android.App;
using Android.Content;
using Android.OS;
using Android.Runtime;
using Android.Views;
using Android.Widget;
using Xamarin.Forms.Platform.Android;
using Xamarin.Forms;
using VHS.MobileApp.eVita.CustomViews;
using Android.Graphics;
using Android.Text.Method;
using Android.Util;
using Color = Xamarin.Forms.Color;
using VHS.MobileApp.eVita.Droid.CustomRenderer;
using System.ComponentModel;
using Android.Text;
[assembly: ExportRenderer(typeof(ExtendedEntry), typeof(ExtendedEntryRenderer))]
namespace VHS.MobileApp.eVita.Droid.CustomRenderer
{
public class ExtendedEntryRenderer : EntryRenderer
{
protected ExtendedEntryRenderer(IntPtr javaReference, JniHandleOwnership transfer)
{
}
public ExtendedEntryRenderer()
: base()
{
}
private const int MinDistance = 10;
/// <summary>
/// Called when [element changed].
/// </summary>
/// <param name="e">The e.</param>
protected override void OnElementChanged(ElementChangedEventArgs<Entry> e)
{
base.OnElementChanged(e);
var view = (ExtendedEntry)Element;
if (Control != null && e.NewElement != null && e.NewElement.IsPassword)
{
Control.SetTypeface(Typeface.Default, TypefaceStyle.Normal);
Control.TransformationMethod = new PasswordTransformationMethod();
this.Control.SetBackgroundColor(Android.Graphics.Color.White);
}
#region SETTING CUSTOM FONT
if (view.FontFamily != null && view.FontFamily != string.Empty)
{
Typeface typeface = Typeface.CreateFromAsset(Forms.Context.Assets, view.FontFamily);
Control.Typeface = typeface;
}
#endregion
// SetFont(view);
SetTextAlignmentWithVerticalFill(view);
SetPlaceholderTextColor(view);
SetMaxLength(view);
}
/// <summary>
/// Handles the touch.
/// </summary>
/// <param name="sender">The sender.</param>
/// <param name="e">The <see cref="Android.Views.View.TouchEventArgs"/> instance containing the event data.</param>
/*void HandleTouch(object sender, TouchEventArgs e)
{
var element = (ExtendedEntry)this.Element;
switch (e.Event.Action)
{
case MotionEventActions.Down:
this.downX = e.Event.GetX();
this.downY = e.Event.GetY();
return;
case MotionEventActions.Up:
case MotionEventActions.Cancel:
case MotionEventActions.Move:
this.upX = e.Event.GetX();
this.upY = e.Event.GetY();
float deltaX = this.downX - this.upX;
float deltaY = this.downY - this.upY;
// swipe horizontal?
if (Math.Abs(deltaX) > Math.Abs(deltaY))
{
if (Math.Abs(deltaX) > MinDistance)
{
if (deltaX < 0)
{
element.OnRightSwipe(this, EventArgs.Empty);
return;
}
if (deltaX > 0)
{
element.OnLeftSwipe(this, EventArgs.Empty);
return;
}
}
else
{
Log.Info("ExtendedEntry", "Horizontal Swipe was only " + Math.Abs(deltaX) + " long, need at least " + MinDistance);
return; // We don't consume the event
}
}
// swipe vertical?
// else
// {
// if(Math.abs(deltaY) > MIN_DISTANCE){
// // top or down
// if(deltaY < 0) { this.onDownSwipe(); return true; }
// if(deltaY > 0) { this.onUpSwipe(); return true; }
// }
// else {
// Log.i(logTag, "Vertical Swipe was only " + Math.abs(deltaX) + " long, need at least " + MIN_DISTANCE);
// return false; // We don't consume the event
// }
// }
return;
}
}*/
/// <summary>
/// Handles the <see cref="E:ElementPropertyChanged" /> event.
/// </summary>
/// <param name="sender">The sender.</param>
/// <param name="e">The <see cref="System.ComponentModel.PropertyChangedEventArgs"/> instance containing the event data.</param>
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
var view = (ExtendedEntry)Element;
this.Control.SetBackgroundColor(Android.Graphics.Color.White);
//if (e.PropertyName == ExtendedEntry.FontProperty.PropertyName)
//{
// SetFont(view);
//}
//else
if (e.PropertyName == ExtendedEntry.XAlignProperty.PropertyName)
{
SetTextAlignmentWithVerticalFill(view);
}
else if (e.PropertyName == ExtendedEntry.HasBorderProperty.PropertyName)
{
//return;
}
else if (e.PropertyName == ExtendedEntry.PlaceholderTextColorProperty.PropertyName)
{
SetPlaceholderTextColor(view);
}
else
{
base.OnElementPropertyChanged(sender, e);
if (e.PropertyName == VisualElement.BackgroundColorProperty.PropertyName)
{
this.Control.SetBackgroundColor(view.BackgroundColor.ToAndroid());
}
}
}
/// <summary>
/// Sets the text alignment.
/// </summary>
/// <param name="view">The view.</param>
private void SetTextAlignmentWithVerticalFill(ExtendedEntry entry)
{
switch (entry.XAlign)
{
case Xamarin.Forms.TextAlignment.Center:
Control.Gravity = GravityFlags.Center;
break;
case Xamarin.Forms.TextAlignment.End:
Control.Gravity = GravityFlags.End | GravityFlags.CenterVertical;
break;
case Xamarin.Forms.TextAlignment.Start:
Control.Gravity = GravityFlags.Start | GravityFlags.CenterVertical;
break;
}
}
/// <summary>
/// Sets the color of the placeholder text.
/// </summary>
/// <param name="view">The view.</param>
private void SetPlaceholderTextColor(ExtendedEntry view)
{
if (view.PlaceholderTextColor != Color.Default)
{
Control.SetHintTextColor(view.PlaceholderTextColor.ToAndroid());
}
}
/// <summary>
/// Sets the MaxLength characteres.
/// </summary>
/// <param name="view">The view.</param>
private void SetMaxLength(ExtendedEntry view)
{
Control.SetFilters(new IInputFilter[] { new InputFilterLengthFilter(view.MaxLength) });
}
}
}
I am trying to figure out a way to make checkbox appear on button click on a page.
It's invisible by default, because I've set checkBox.Visibility = Android.Views.ViewStates.Invisible; in my custom renderer.
I have a button in the page content and a checkbox in the template which resides in pages resources.
From my ViewModel I am able to invoke PropertyChanged in CheckBox control where I can see the old and new value correctly set.
But I need a way to set it on the ViewRenderer. I'm guessing that it needs to handle some kind of event similar to CheckedChanged.
ViewModel
CheckBox c = new CheckBox { IsCheckBoxVisible=true,IsVisible=true };
CheckBox control
public class CheckBox : View
{
/// <summary>
/// The checked state property.
/// </summary>
public static readonly BindableProperty CheckedProperty =
BindableProperty.Create<CheckBox, bool>(
p => p.Checked, false, BindingMode.TwoWay, propertyChanged: OnCheckedPropertyChanged);
**public static readonly BindableProperty IsCheckBoxVisibleProperty =
BindableProperty.Create<CheckBox, bool>(
p => p.IsCheckBoxVisible, false, BindingMode.OneWay, propertyChanged: OnVisibilityPropertyChanged);**
/// <summary>
/// The checked text property.
/// </summary>
public static readonly BindableProperty CheckedTextProperty =
BindableProperty.Create<CheckBox, string>(
p => p.CheckedText, string.Empty, BindingMode.TwoWay);
/// <summary>
/// The unchecked text property.
/// </summary>
public static readonly BindableProperty UncheckedTextProperty =
BindableProperty.Create<CheckBox, string>(
p => p.UncheckedText, string.Empty);
/// <summary>
/// The default text property.
/// </summary>
public static readonly BindableProperty DefaultTextProperty =
BindableProperty.Create<CheckBox, string>(
p => p.Text, string.Empty);
/// <summary>
/// Identifies the TextColor bindable property.
/// </summary>
///
/// <remarks/>
public static readonly BindableProperty TextColorProperty =
BindableProperty.Create<CheckBox, Color>(
p => p.TextColor, Color.Default);
/// <summary>
/// The font size property
/// </summary>
public static readonly BindableProperty FontSizeProperty =
BindableProperty.Create<CheckBox, double>(
p => p.FontSize, -1);
/// <summary>
/// The font name property.
/// </summary>
public static readonly BindableProperty FontNameProperty =
BindableProperty.Create<CheckBox, string>(
p => p.FontName, string.Empty);
/// <summary>
/// The checked changed event.
/// </summary>
public event EventHandler<EventArgs<bool>> CheckedChanged;
**public event EventHandler<EventArgs<bool>> VisibilityChanged;**
/// <summary>
/// Gets or sets a value indicating whether the control is checked.
/// </summary>
/// <value>The checked state.</value>
public bool Checked
{
get
{
return this.GetValue<bool>(CheckedProperty);
}
set
{
if (this.Checked != value)
{
this.SetValue(CheckedProperty, value);
this.CheckedChanged.Invoke(this, value);
}
}
}
**public bool IsCheckBoxVisible
{
get
{
return this.GetValue<bool>(IsCheckBoxVisibleProperty);
}
set
{
if (this.IsCheckBoxVisible != value)
{
this.SetValue(IsCheckBoxVisibleProperty, value);
this.VisibilityChanged.Invoke(this, value);
//OnPropertyChanged("IsCheckBoxVisible");
}
}
}**
/// <summary>
/// Gets or sets a value indicating the checked text.
/// </summary>
/// <value>The checked state.</value>
/// <remarks>
/// Overwrites the default text property if set when checkbox is checked.
/// </remarks>
public string CheckedText
{
get
{
return this.GetValue<string>(CheckedTextProperty);
}
set
{
this.SetValue(CheckedTextProperty, value);
}
}
/// <summary>
/// Gets or sets a value indicating whether the control is checked.
/// </summary>
/// <value>The checked state.</value>
/// <remarks>
/// Overwrites the default text property if set when checkbox is checked.
/// </remarks>
public string UncheckedText
{
get
{
return this.GetValue<string>(UncheckedTextProperty);
}
set
{
this.SetValue(UncheckedTextProperty, value);
}
}
/// <summary>
/// Gets or sets the text.
/// </summary>
public string DefaultText
{
get
{
return this.GetValue<string>(DefaultTextProperty);
}
set
{
this.SetValue(DefaultTextProperty, value);
}
}
/// <summary>
/// Gets or sets the color of the text.
/// </summary>
/// <value>The color of the text.</value>
public Color TextColor
{
get
{
return this.GetValue<Color>(TextColorProperty);
}
set
{
this.SetValue(TextColorProperty, value);
}
}
/// <summary>
/// Gets or sets the size of the font.
/// </summary>
/// <value>The size of the font.</value>
public double FontSize
{
get
{
return (double)GetValue(FontSizeProperty);
}
set
{
SetValue(FontSizeProperty, value);
}
}
/// <summary>
/// Gets or sets the name of the font.
/// </summary>
/// <value>The name of the font.</value>
public string FontName
{
get
{
return (string)GetValue(FontNameProperty);
}
set
{
SetValue(FontNameProperty, value);
}
}
/// <summary>
/// Gets the text.
/// </summary>
/// <value>The text.</value>
public string Text
{
get
{
return this.Checked
? (string.IsNullOrEmpty(this.CheckedText) ? this.DefaultText : this.CheckedText)
: (string.IsNullOrEmpty(this.UncheckedText) ? this.DefaultText : this.UncheckedText);
}
}
/// <summary>
/// Called when [checked property changed].
/// </summary>
/// <param name="bindable">The bindable.</param>
/// <param name="oldvalue">if set to <c>true</c> [oldvalue].</param>
/// <param name="newvalue">if set to <c>true</c> [newvalue].</param>
private static void OnCheckedPropertyChanged(BindableObject bindable, bool oldvalue, bool newvalue)
{
var checkBox = (CheckBox)bindable;
checkBox.Checked = newvalue;
}
**private static void OnVisibilityPropertyChanged(BindableObject bindable, bool oldvalue, bool newvalue)
{
var checkBox = (CheckBox)bindable;
checkBox.IsCheckBoxVisible = newvalue;
}**
}
CheckBoxRenderer
protected override void OnElementChanged(ElementChangedEventArgs e)
{
base.OnElementChanged(e);
if (this.Control == null)
{
var checkBox = new Android.Widget.CheckBox(this.Context);
checkBox.Visibility = Android.Views.ViewStates.Invisible;
checkBox.CheckedChange += CheckBoxCheckedChange;
defaultTextColor = checkBox.TextColors;
this.SetNativeControl(checkBox);
}
Control.Text = e.NewElement.Text;
Control.Checked = e.NewElement.Checked;
UpdateTextColor();
if (e.NewElement.FontSize > 0)
{
Control.TextSize = (float)e.NewElement.FontSize;
}
if (!string.IsNullOrEmpty(e.NewElement.FontName))
{
Control.Typeface = TrySetFont(e.NewElement.FontName);
}
}
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
switch (e.PropertyName)
{
case "Checked":
Control.Text = Element.Text;
Control.Checked = Element.Checked;
break;
case "TextColor":
UpdateTextColor();
break;
case "FontName":
if (!string.IsNullOrEmpty(Element.FontName))
{
Control.Typeface = TrySetFont(Element.FontName);
}
break;
case "FontSize":
if (Element.FontSize > 0)
{
Control.TextSize = (float)Element.FontSize;
}
break;
case "CheckedText":
case "UncheckedText":
Control.Text = Element.Text;
break;
** case "IsCheckBoxVisible":
if(Element.IsCheckBoxVisible==true)
{
Control.Visibility = Android.Views.ViewStates.Visible;
}
else
{
Control.Visibility = Android.Views.ViewStates.Invisible;
}
break;**
default:
System.Diagnostics.Debug.WriteLine("Property change for {0} has not been implemented.", e.PropertyName);
break;
}
}
So this should actually be really simple. right now you have IsCheckBoxVisibleProperty, and you can get rid of it all together. The Xamarin.Forms.View already has an IsVisible property, and each platform specific renderer (VisualElementRenderer) knows how to handle visibility.
Therefore you can do this without issue.
var checkbox = new Checkbox();
checkbox .SetBinding (Checkbox.IsVisibleProperty, "IsCheckboxVisible");
Or in your XAML
<controls:Checkbox IsVisible="{Binding IsCheckboxVisible}" />
Of course this assumes you have a ViewModel similar to.
public class MyViewModel : BaseViewModel
{
private bool _isCheckboxVisible;
public bool IsCheckboxVisible
{
get { return _isCheckboxVisible; }
set { SetField(ref _isCheckboxVisible, value); }
}
}
In latest version of Facebook C# SDk 6.4. Can we use FacebookSubscriptionVerify Action Method Attribute ? As this is not available in the FacebookClient Class
I was using the older version of Facebok C# SDK in my MVC3 project. Now, After switching to Facebook C# SDK 6.4 this class is not available.
Do we have any substitute for this?
I took a little more time this morning and confirmed that the attribute that you referenced was removed in version 6 (along with tons of other items). Since this project is open source, here is the code for the FacebookSubscriptionVerify ActionFilter that you used to use. For any references to functions within here that I did not include, this version on CodePlex has all of the code available for you to look at: http://facebooksdk.codeplex.com/SourceControl/changeset/view/08cb51f372b5#Source/Facebook.Web/FacebookSubscriptionsHttpHandler.cs
The new version (version 6.X) and the last few branches of version 5 can be found on the GitHub site - https://github.com/facebook-csharp-sdk/facebook-csharp-sdk/tree/master/Source
With the availability of the source code, you should be able to, in tandem with how you were using this function, create your own ActionFilterAttribute that can replicate the functionality that you had previously.
// --------------------------------
// <copyright file="FacebookSubscriptionVerifyAttribute.cs" company="Thuzi LLC (www.thuzi.com)">
// Microsoft Public License (Ms-PL)
// </copyright>
// <author>Nathan Totten (ntotten.com), Jim Zimmerman (jimzimmerman.com) and Prabir Shrestha (prabir.me)</author>
// <license>Released under the terms of the Microsoft Public License (Ms-PL)</license>
// <website>http://facebooksdk.codeplex.com</website>
// ---------------------------------
namespace Facebook.Web.Mvc
{
using System.Web.Mvc;
public class FacebookSubscriptionVerifyAttribute : ActionFilterAttribute
{
public string VerificationToken { get; set; }
public FacebookSubscriptionVerifyAttribute(string verificationToken)
{
VerificationToken = verificationToken;
}
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
filterContext.HttpContext.Response.ContentType = "text/plain";
var request = filterContext.HttpContext.Request;
var modelState = filterContext.Controller.ViewData.ModelState;
string errorMessage;
if (request.HttpMethod == "GET")
{
if (string.IsNullOrEmpty(VerificationToken))
{
errorMessage = "Verification Token is empty.";
}
else
{
if (FacebookSubscriptionVerifier.VerifyGetSubscription(request, VerificationToken, out errorMessage))
{
return;
}
}
}
else
{
errorMessage = "Invalid http method.";
}
modelState.AddModelError("facebook-subscription", errorMessage);
filterContext.HttpContext.Response.StatusCode = 401;
}
}
}
And the code for the FacebookSubscriptionVerifier Class
namespace Facebook.Web
{
using System.Collections.Generic;
using System.Diagnostics.Contracts;
using System.Globalization;
using System.Linq;
using System.Text;
using System.Web;
/// <summary>
/// Facebook helper methods for web.
/// </summary>
internal static class FacebookSubscriptionVerifier
{
internal const string HTTP_X_HUB_SIGNATURE_KEY = "HTTP_X_HUB_SIGNATURE";
internal static byte[] ComputeHmacSha1Hash(byte[] data, byte[] key)
{
Contract.Requires(data != null);
Contract.Requires(key != null);
Contract.Ensures(Contract.Result<byte[]>() != null);
using (var crypto = new System.Security.Cryptography.HMACSHA1(key))
{
return crypto.ComputeHash(data);
}
}
/// <summary>
/// Verify HTTP_X_HUB_SIGNATURE.
/// </summary>
/// <param name="secret">
/// The secret.
/// </param>
/// <param name="httpXHubSignature">
/// The http x hub signature.
/// </param>
/// <param name="jsonString">
/// The json string.
/// </param>
/// <returns>
/// Returns true if validation is successful.
/// </returns>
internal static bool VerifyHttpXHubSignature(string secret, string httpXHubSignature, string jsonString)
{
Contract.Requires(!string.IsNullOrEmpty(secret));
if (!string.IsNullOrEmpty(httpXHubSignature) && httpXHubSignature.StartsWith("sha1=") && httpXHubSignature.Length > 5 && !string.IsNullOrEmpty(jsonString))
{
// todo: test inner parts
var expectedSignature = httpXHubSignature.Substring(5);
var sha1 = ComputeHmacSha1Hash(Encoding.UTF8.GetBytes(jsonString), Encoding.UTF8.GetBytes(secret));
var hashString = new StringBuilder();
foreach (var b in sha1)
{
hashString.Append(b.ToString("x2"));
}
if (expectedSignature == hashString.ToString())
{
return true;
}
}
return false;
}
/// <summary>
/// Verify HTTP_X_HUB_SIGNATURE for http GET method.
/// </summary>
/// <param name="request">
/// The http request.
/// </param>
/// <param name="verifyToken">
/// The verify token.
/// </param>
/// <param name="errorMessage">
/// The error message.
/// </param>
/// <returns>
/// Returns true if successful otherwise false.
/// </returns>
internal static bool VerifyGetSubscription(HttpRequestBase request, string verifyToken, out string errorMessage)
{
Contract.Requires(request != null);
Contract.Requires(request.HttpMethod == "GET");
Contract.Requires(request.Params != null);
Contract.Requires(!string.IsNullOrEmpty(verifyToken));
errorMessage = null;
if (request.Params["hub.mode"] == "subscribe")
{
if (request.Params["hub.verify_token"] == verifyToken)
{
if (string.IsNullOrEmpty(request.Params["hub.challenge"]))
{
errorMessage = Properties.Resources.InvalidHubChallenge;
}
else
{
return true;
}
}
else
{
errorMessage = Properties.Resources.InvalidVerifyToken;
}
}
else
{
errorMessage = Properties.Resources.InvalidHubMode;
}
return false;
}
/// <summary>
/// Verify HTTP_X_HUB_SIGNATURE for http POST method.
/// </summary>
/// <param name="request">
/// The request.
/// </param>
/// <param name="secret">
/// The secret.
/// </param>
/// <param name="jsonString">
/// The json string.
/// </param>
/// <param name="errorMessage">
/// The error message.
/// </param>
/// <returns>
/// Returns true if successful otherwise false.
/// </returns>
internal static bool VerifyPostSubscription(HttpRequestBase request, string secret, string jsonString, out string errorMessage)
{
Contract.Requires(request != null);
Contract.Requires(request.HttpMethod == "POST");
Contract.Requires(request.Params != null);
Contract.Requires(!string.IsNullOrEmpty(secret));
errorMessage = null;
// signatures looks somewhat like "sha1=4594ae916543cece9de48e3289a5ab568f514b6a"
var signature = request.Params["HTTP_X_HUB_SIGNATURE"];
if (!string.IsNullOrEmpty(signature) && signature.StartsWith("sha1="))
{
var expectedSha1 = signature.Substring(5);
if (string.IsNullOrEmpty(expectedSha1))
{
errorMessage = Properties.Resources.InvalidHttpXHubSignature;
}
else
{
if (string.IsNullOrEmpty(jsonString))
{
errorMessage = Properties.Resources.InvalidJsonString;
return false;
}
var sha1 = ComputeHmacSha1Hash(Encoding.UTF8.GetBytes(jsonString), Encoding.UTF8.GetBytes(secret));
var hashString = new StringBuilder();
foreach (var b in sha1)
{
hashString.Append(b.ToString("x2"));
}
if (expectedSha1 == hashString.ToString())
{
// todo: test
return true;
}
// todo: test
errorMessage = Properties.Resources.InvalidHttpXHubSignature;
}
}
else
{
errorMessage = Properties.Resources.InvalidHttpXHubSignature;
}
return false;
}
}
}
This question already has answers here:
Closed 11 years ago.
Possible Duplicate:
Find IMEI no in wp7?
Is there any api that gets the device IMEI number in windows phone 7, all i can get it "device unique id" by using DeviceExtendedProperties.GetValue("DeviceUniqueId"), but i need to get IMEI.
cc:http://www.cnblogs.com/xjb/archive/2007/02/05/640360.html
the following code is not tested by me.
public struct GeneralInfo
{
public string Manufacturer;
public string Model;
public string Revision;
public string SerialNumber;
public string SubscriberNumber;
}
/// <summary>
/// Tapi control class
/// </summary>
public class ControlTapi
{
[DllImport("cellcore.dll")]
private static extern int lineGetGeneralInfo(IntPtr hLigne,byte[]lpLineGeneralInfo );
/// <summary>
/// Invoke cellcore.dll to get info of sim
/// </summary>
/// <param name="l"></param>
/// <returns></returns>
private GeneralInfo GetGeneralInfo(Line l)
{
GeneralInfo lgi = new GeneralInfo();
byte[] buffer = new byte[512];
BitConverter.GetBytes(512).CopyTo(buffer, 0);
if (lineGetGeneralInfo(l.hLine, buffer) != 0)
{
throw new System.ComponentModel.Win32Exception(System.Runtime.InteropServices.Marshal.GetLastWin32Error(), "TAPI Error: " + System.Runtime.InteropServices.Marshal.GetLastWin32Error().ToString("X"));
}
int subscsize = BitConverter.ToInt32(buffer, 44);
int subscoffset = BitConverter.ToInt32(buffer, 48);
lgi.SubscriberNumber = System.Text.Encoding.Unicode.GetString(buffer, subscoffset, subscsize).ToString();
lgi.SubscriberNumber = lgi.SubscriberNumber.Replace("\0", "");
return lgi;
}
/// <summary>
/// GET IMSI of SIM Card
/// </summary>
/// <returns></returns>
public static string GetIMSINumber()
{
string result = "";
try
{
Tapi t = new Tapi();
t.Initialize();
Line l = t.CreateLine(0, LINEMEDIAMODE.INTERACTIVEVOICE, OpenNETCF.Tapi.LINECALLPRIVILEGE.MONITOR);
ControlTapi ctapi = new ControlTapi();
GeneralInfo gi = ctapi.GetGeneralInfo(l);
result = gi.SubscriberNumber;
l.Dispose();
t.Shutdown();
}
catch// (Exception ex)
{
result = "";
}
return result;
}
/// <summary>
/// Get IMEI
/// </summary>
/// <returns></returns>
public static string GetIMEINumber()
{
string result = "";
try
{
Tapi t = new Tapi();
t.Initialize();
Line l = t.CreateLine(0, LINEMEDIAMODE.INTERACTIVEVOICE, OpenNETCF.Tapi.LINECALLPRIVILEGE.MONITOR);
ControlTapi ctapi = new ControlTapi();
GeneralInfo gi = ctapi.GetGeneralInfo(l);
result = gi.SerialNumber;
l.Dispose();
t.Shutdown();
}
catch// (Exception ex)
{
result = "";
}
return result;
}
}