Xamarin.iOS UIApperance setDefaultTextAttributes
Xamarin.iOS UIApperance setDefaultTextAttributes
我正在尝试弄清楚如何在 Xamarin 中实现以下代码:
[[UITextField appearanceWhenContainedIn:[UISearchBar class], nil] setDefaultTextAttributes:@{NSForegroundColorAttributeName:[UIColor greenColor]}];
但是我找不到在 UIApperance 上设置 DefaultTextAttributes 的方法 class。
在 Xamarin.iOS 中有 个缺失的 UIAppearance
个特征,关于你的问题,缺失 API.
- 这是一个错误,我自己编写了
UIAppearance.cs
来添加缺失的功能并更正缺失的 API 和 假设 没有其他 Xamarin.iOS 编码人员真正使用较新的 UIAppearance
功能,因为它自 Xamarin 中的 iOS 9 以来已被破坏。
首先,appearanceWhenContainedIn
已弃用,您应该改用 appearanceWhenContainedInInstancesOfClasses
。
AppearanceWhenContainedIn - was deprecated in iOS 9 and is not recommended for use.
其次,appearanceWhenContainedInInstancesOfClasses
在 Xamarin.iOS
中被 错误地 定义为 仅在 tvOS
中可用 事实并非如此。
#if TVOS
// new in iOS9 but the only option for tvOS
const string selAppearanceWhenContainedInInstancesOfClasses = "appearanceWhenContainedInInstancesOfClasses:";
~~~
更新:我提交了一个关于此的 Github 问题。
因此它不能通过 Xamarin.iOS 包装器 API 使用,但当然可以直接从 ObjC 运行时使用:
var NSForegroundColorAttributeName = Dlfcn.GetStringConstant(UIKitLibraryHandle, "NSForegroundColorAttributeName");
var defaultAttributes = NSDictionary.FromObjectsAndKeys(new NSObject[] { UIColor.Red }, new NSObject[] { NSForegroundColorAttributeName });
var styleHandle = GetAppearanceEx(Class.GetHandle("UITextField"), typeof(UISearchBar));
void_objc_msgSend_IntPtr(styleHandle, Selector.GetHandle("setDefaultTextAttributes:"), defaultAttributes.Handle);
下一个问题有许多 Xamarin.iOS 标记为 internal 的方法是上述代码运行所必需的,所以一些 copy/paste/modify 一些需要来源:
public const string selAppearanceWhenContainedInInstancesOfClasses = "appearanceWhenContainedInInstancesOfClasses:";
public static readonly IntPtr UIKitLibraryHandle = Dlfcn.dlopen("/System/Library/Frameworks/UIKit.framework/UIKit", 0);
[DllImport("/usr/lib/libobjc.dylib", EntryPoint = "objc_msgSend")]
public static extern IntPtr IntPtr_objc_msgSend_IntPtr(IntPtr receiver, IntPtr selector, IntPtr arg1);
[DllImport("/usr/lib/libobjc.dylib", EntryPoint = "objc_msgSend")]
public static extern void void_objc_msgSend_IntPtr(IntPtr receiver, IntPtr selector, IntPtr arg1);
public static IntPtr GetAppearanceEx(IntPtr class_ptr, params Type[] whenFoundIn)
{
var ptrs = TypesToPointers(whenFoundIn);
var handles = NSArray.FromIntPtrs(ptrs);
using (var array = handles)
{
return IntPtr_objc_msgSend_IntPtr(class_ptr, Selector.GetHandle(selAppearanceWhenContainedInInstancesOfClasses), array.Handle);
}
}
public static IntPtr[] TypesToPointers(Type[] whenFoundIn)
{
IntPtr[] ptrs = new IntPtr[whenFoundIn.Length];
for (int i = 0; i < whenFoundIn.Length; i++)
{
if (whenFoundIn[i] == null)
throw new ArgumentException(String.Format("Parameter {0} was null, must specify a valid type", i));
if (!typeof(NSObject).IsAssignableFrom(whenFoundIn[i]))
throw new ArgumentException(String.Format("Type {0} does not derive from NSObject", whenFoundIn[i]));
var classHandle = Class.GetHandle(whenFoundIn[i]);
if (classHandle == IntPtr.Zero)
throw new ArgumentException(string.Format("Could not find the Objective-C class for {0}", whenFoundIn[i].FullName));
ptrs[i] = classHandle;
}
return ptrs;
}
我正在尝试弄清楚如何在 Xamarin 中实现以下代码:
[[UITextField appearanceWhenContainedIn:[UISearchBar class], nil] setDefaultTextAttributes:@{NSForegroundColorAttributeName:[UIColor greenColor]}];
但是我找不到在 UIApperance 上设置 DefaultTextAttributes 的方法 class。
在 Xamarin.iOS 中有 个缺失的 UIAppearance
个特征,关于你的问题,缺失 API.
- 这是一个错误,我自己编写了
UIAppearance.cs
来添加缺失的功能并更正缺失的 API 和 假设 没有其他 Xamarin.iOS 编码人员真正使用较新的UIAppearance
功能,因为它自 Xamarin 中的 iOS 9 以来已被破坏。
首先,appearanceWhenContainedIn
已弃用,您应该改用 appearanceWhenContainedInInstancesOfClasses
。
AppearanceWhenContainedIn - was deprecated in iOS 9 and is not recommended for use.
其次,appearanceWhenContainedInInstancesOfClasses
在 Xamarin.iOS
中被 错误地 定义为 仅在 tvOS
中可用 事实并非如此。
#if TVOS
// new in iOS9 but the only option for tvOS
const string selAppearanceWhenContainedInInstancesOfClasses = "appearanceWhenContainedInInstancesOfClasses:";
~~~
更新:我提交了一个关于此的 Github 问题。
因此它不能通过 Xamarin.iOS 包装器 API 使用,但当然可以直接从 ObjC 运行时使用:
var NSForegroundColorAttributeName = Dlfcn.GetStringConstant(UIKitLibraryHandle, "NSForegroundColorAttributeName");
var defaultAttributes = NSDictionary.FromObjectsAndKeys(new NSObject[] { UIColor.Red }, new NSObject[] { NSForegroundColorAttributeName });
var styleHandle = GetAppearanceEx(Class.GetHandle("UITextField"), typeof(UISearchBar));
void_objc_msgSend_IntPtr(styleHandle, Selector.GetHandle("setDefaultTextAttributes:"), defaultAttributes.Handle);
下一个问题有许多 Xamarin.iOS 标记为 internal 的方法是上述代码运行所必需的,所以一些 copy/paste/modify 一些需要来源:
public const string selAppearanceWhenContainedInInstancesOfClasses = "appearanceWhenContainedInInstancesOfClasses:";
public static readonly IntPtr UIKitLibraryHandle = Dlfcn.dlopen("/System/Library/Frameworks/UIKit.framework/UIKit", 0);
[DllImport("/usr/lib/libobjc.dylib", EntryPoint = "objc_msgSend")]
public static extern IntPtr IntPtr_objc_msgSend_IntPtr(IntPtr receiver, IntPtr selector, IntPtr arg1);
[DllImport("/usr/lib/libobjc.dylib", EntryPoint = "objc_msgSend")]
public static extern void void_objc_msgSend_IntPtr(IntPtr receiver, IntPtr selector, IntPtr arg1);
public static IntPtr GetAppearanceEx(IntPtr class_ptr, params Type[] whenFoundIn)
{
var ptrs = TypesToPointers(whenFoundIn);
var handles = NSArray.FromIntPtrs(ptrs);
using (var array = handles)
{
return IntPtr_objc_msgSend_IntPtr(class_ptr, Selector.GetHandle(selAppearanceWhenContainedInInstancesOfClasses), array.Handle);
}
}
public static IntPtr[] TypesToPointers(Type[] whenFoundIn)
{
IntPtr[] ptrs = new IntPtr[whenFoundIn.Length];
for (int i = 0; i < whenFoundIn.Length; i++)
{
if (whenFoundIn[i] == null)
throw new ArgumentException(String.Format("Parameter {0} was null, must specify a valid type", i));
if (!typeof(NSObject).IsAssignableFrom(whenFoundIn[i]))
throw new ArgumentException(String.Format("Type {0} does not derive from NSObject", whenFoundIn[i]));
var classHandle = Class.GetHandle(whenFoundIn[i]);
if (classHandle == IntPtr.Zero)
throw new ArgumentException(string.Format("Could not find the Objective-C class for {0}", whenFoundIn[i].FullName));
ptrs[i] = classHandle;
}
return ptrs;
}