通用应用中的条件编译






4.94/5 (14投票s)
在通用 Windows 应用中共享代码和视图
- 下载 ConditionalCompilation.zip - 216.7 KB
- 下载 ConditionalCompilation.rar - 189.7 KB
- 下载 ConditionalCompilationOfXaml.rar - 218.9 KB
- 下载 ConditionalCompilationOfXaml.zip - 246.6 KB
引言
条件编译是指定义编译器指令的过程,这些指令会导致代码的不同部分被编译,而其他部分被忽略。这项技术可以在跨平台开发场景中使用,以指定特定于某个平台而被编译的代码部分。[1]
条件编译允许编译器在编译时根据条件子句跳过源代码的某些部分。#if、#endif、#elif 和 #else 指令用于条件编译。这些指令为源文件的一部分添加条件。使用这些指令,我们可以维护一个单一的源文件。
#if CONDITION
//some code
#else
//some code
#endif
它告诉编译器哪些代码需要为项目进行编译。
条件的值决定包含哪个代码块。
conditional-symbol
任何标识符或关键字,除了 true 或 false
条件编译指令应始终以集合的形式编写,顺序为:#if 指令、零个或多个 #elif 指令、零个或一个 #else 指令,以及一个 #endif 指令。在这些指令之间,我们需要编写条件代码。
假设我们需要某些代码仅在某个条件为真时才编译,我们将使用普通的 if else 语句定义一个条件。这对于我们在共享项目上工作非常有用。
这是另一个 C# 示例:
public int calculate(int input)
{
int result;
#if CONDITION
result= input + 10;
#else
result= input - 10;
#endif
return result;
}
Condition 的值将决定功能。
已设置 CONDITION
result = input + 10;
未设置 CONDITION
result = input - 10;
何时使用条件编译
使用条件编译,我们可以隔离特定于平台的代码,因此我们可以根据需要将其用于任何地方。但是,如果我们处理一个大型项目,它会使我们的代码难以管理。.Portable Class Library 无法使用条件编译,因为编译时它只生成一个二进制文件。
Windows 应用中的条件编译
在通用应用中,通过使用条件编译,我们可以编写可针对不同平台(即 Windows Store 和 Windows Phone)的代码。我们可以选择为不同的项目编译哪些代码,因为这两个项目都编译成不同的包。
这是定义特定于平台的代码的最简单方法。例如,我们可以尝试共享我们的代码库,用于 Windows Phone 和 Windows Store 应用,并通过将特定于平台的代码围绕一个条件来改变代码的行为,该条件可以根据我们正在为哪个应用或平台进行编译来设置。通过以下示例,这一点将更加清晰。
这是通用 Windows 应用中条件编译的示例。
首先,我们使用一个空白模板创建一个 C# 通用应用。该解决方案由三个项目组成:一个 Windows Store 应用、一个 Windows Phone 应用和一个共享项目。
解决方案中首先注意到的是,Windows Store 应用和 Windows Phone 应用都有一个单独的起始页,即 Main Page。但我们需要共享这个页面,所以我们只需将其拖到共享项目中,然后删除另外两个项目中的 Main Page。这不会造成任何问题,因为它只是一个空白页面。
现在我们有了一个通用的共享 Main Page。
以前
操作后
在共享项目的 Main Page 中,我们创建了一个简单的 UI,只有一个带有事件处理程序的 Button 和一个 TextBlock,我们希望在单击按钮时,如果它是 Windows Store 应用,则显示“Windows Store”,如果它是 Windows Phone 应用,则显示“Windows Phone”。
我们将通过按钮单击事件处理程序中的条件编译来实现这一点。
我们将添加条件。
#if WINDOWS_APP
#elif WINDOWS_PHONE_APP
我们可以通过转到 Properties->Build->Conditional compilation symbols 来查看此条件。
在 Windows 属性中,已定义的条件编译符号是 NETFX_CORE 和 WINDOWS_APP,而在 Windows Phone 属性中,是 NETFX_CORE 和 WINDOWS_PHONE_APP。
Windows 8 有一个名为 NETFX_CORE 的编译器指令集。因此,对于 Windows 8 项目,它始终是设置好的,并且在 Windows Store 和 Windows Phone 中通用。
我们甚至可以添加自己的编译条件,例如“MY_COMPILATION_CONDITION”,并在我们的项目中进行使用,但让我们使用默认的。
这里的条件是,如果它是 Windows Phone 应用程序,我们希望显示“Windows Phone”,否则我们希望显示“Windows store”。因此,在事件处理程序中,我们将使用条件编译。
我们可以看到一些代码是灰色的,这仅仅是因为 IntelliSense 正在帮助我们进行条件编译。我们可以从顶部的下拉菜单在 Windows 和 Windows Phone 之间切换。我们在这里可以看到我们的平台设置为 Windows,所以与其他平台相关的代码是灰色的。这是一个非常有用的功能,因为我们可以轻松地注意到哪些代码将针对特定平台进行编译。
右键单击 Windows 项目并选择“设置为启动项目”。现在,如果我们通过单击按钮运行 Windows 应用,我们将得到
如果我们选择 Windows Phone 作为启动项目并运行项目,Windows Phone 项目将运行,并且我们可以看到它显示的是 Windows Phone 而不是 Windows Store。
共享视图的另一种方法是
XAML 中的条件编译
如果在共享项目中使用了 TopAppBar,应用程序将在 Windows Store 中完美运行,但在 Windows Phone 中会出现异常,因为 TopAppBar 在 Windows Phone 上不可用。
通过使用 XAML 条件编译来管理 Windows 和 Windows Phone 之间 XAML 差异的好方法是。XCC 是一个预处理器,为 XAML 文件添加条件编译支持。我们可以通过安装一个非常小的 NuGet 包来在项目中启用 XCC。它支持 Windows Universal 应用和 Xamarin Forms 项目。
我们将通过 NuGet 包管理器添加此内容。我们将对解决方案进行此操作,因为我们需要将其添加到两个项目中。每当我们从共享项目引用任何库或包时,都需要将其添加到两个项目中。
打开解决方案上下文菜单,选择“管理解决方案的 NuGet 包”。搜索 xcc 并将 XAML Conditional Compilation NuGet 包安装到两个项目中。
添加 NuGet 包后,我们必须在要使用它的 Main Page 中声明它。
我们正在为 Windows 应用和 Windows Phone 应用添加条件。
xmlns:win="condition:WINDOWS_APP"
xmlns:wp="condition:WINDOWS_PHONE_APP"
xmlns:win 和 xmlns:wp 属性定义了条件编译的 XML 元素和属性的命名空间。当我们要仅为 Windows Store 应用编译代码时,使用 xmlns:win;当我们要仅为 Windows Phone 应用编译代码时,使用 xmlns:wp。
我们还必须将其添加到要忽略的列表中,否则 VS 会报错。
mc:Ignorable="d win wp"
mc:Ignorable 属性确保新的 xmlns 前缀被设计器和编译器忽略。
有了条件编译命名空间后,我们就可以输入以下 XAML 了。现在我们只需要在控件前添加“win”或“wp”前缀。在我们上面的例子中,我们希望我们的 TopAppBar 仅在是 Windows Store 应用程序时显示,所以我们将“win”添加到“Page.TopAppBar”。
我还添加了“wp”到“Page.BottomAppBar”。现在它只会编译到 Windows Phone 应用程序。
如果运行 Windows 应用,它只会显示 Top App Bar。
如果运行 Windows Phone App,它只会显示 Command Bar。
当我们在 XML 元素上应用自定义前缀时,IntelliSense 不会起作用。但我们可以通过添加 **mc:ProcessContent** 属性来启用 IntelliSense 支持。
mc:ProcessContent="win:* wp:*"
mc:ProcessContent 属性在条件区域内启用 IntelliSense。
技巧和最佳实践
不要使用 #else if、#elseif 或 #elsif,它们不会起作用。您可以使用 #elif 代替。
XCC 仍处于测试阶段,请谨慎使用。
如果我们对特定控件使用 XCC,我们在设计时将无法看到它。我的诀窍是先进行设计,当我对它满意后,再应用条件编译。
关注点
通用 Windows 应用可以节省时间。我们可以同时为 Windows 和 Windows Phone 构建一个应用,并在 Visual Studio 中共享代码、用户控件、样式、字符串和其他资产。这减少了为每种设备类型构建和维护应用的成本和时间。
历史
文章 V1。
参考文献
https://msdn.microsoft.com/en-us/library/windows/apps/jj714084%28v=vs.105%29.aspx?f=255&MSPPError=-2147217396
https://github.com/firstfloorsoftware/xcc/wiki
https://xcc.codeplex.com/wikipage?title=Xamarin%20Forms