@

引言

自学的C#,看了几本教材讲的都是程序代码,网上找的也有视屏,但都比较老了。只会打些代码为不晓得为什么要这样打感觉很别扭,在朋友的推荐下先选择了这本《Head First C#》先大致的了解下C#。

这本书的第一章我就遇见了问题,要装IDE选的是VS2012 for win8的,这完全和我的系统不配我是用的VS2017+win10,想着应该是一样的,但是没有找到windows store,我寻思着估计我只安装了for .NET没有安装windows平台通用的那个环境,要是选择在安装那个环境的话12G空间,懒得装。书上说明了使用WPF可以打大部分代码,那就将就着用吧!书上给了参考PDF的下载网址可是用梯子也连不上,打了前缀发现进了他们公司的主站。估计网址换了把,CSDN上也没找到那个PDF资源。自己瞎琢磨着来吧,这个博客是个记录,希望对你有用。

前期工作

  1. 打开VS,创建WPF窗体;

  2. 照书上一步一步来搭建界面,基本一样

  3. 搭建好了我们就来写代码,代码里面有点不一样我会说明的

代码编写

注意事项:

  1. 引用的地方:这里你会发现没有using windows.UI.Xaml;之类的引用。这是你没安装他的环境因而没有这些动态库。

    解决方法:用using System.Windows.*,就行,你会发现其实去掉UI,Xaml其他字段都一样。
  2. 关于事件里面没有PointerPressed和PointerMoved等等这个它可以发布到平台上平板也要用估计是他们把事件给优化了,不过不用慌,看得懂英文的就可以类推不就是个鼠标按压事件和鼠标移动事件吗?照着我们有的事件来就行。

    解决方法:使用MouseDown和MouseMoved代替其他事件一样。
  3. PlayArea_MouseMove函数里面有个Point的语句,是不是按照书上敲又报错了!这个我也不晓得为啥给可能还是环境的问题吧!.NET的WPF确实没有那几个函数。不过仔细读下就可以理解是获取PlayArea里面的鼠标位置,进行鼠标位置判断的。网上查了下WPF获取鼠标位置的几种方法这发现使用这种更合适跟简单,还不用像书上那样进行鼠标的转换,用e.GetPosition(playArea);直接就使用的是相对与playArea的鼠标位置。

    解决办法:使用e.GetPosition()

其他的倒没有什么问题,有问题留言,如果我可以帮助你的话。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes; using System.Windows.Media.Animation;
using System.Windows.Threading; namespace SaveHuman
{
/// <summary>
/// MainWindow.xaml 的交互逻辑
/// </summary>
public partial class MainWindow : Window
{
Random random = new Random();
DispatcherTimer enemyTimer = new DispatcherTimer();
DispatcherTimer targetTimer = new DispatcherTimer();
bool humanCaptured = false;
public MainWindow()
{
InitializeComponent(); enemyTimer.Tick += EnemyTimer_Tick;//2019.10.30 22点21分
enemyTimer.Interval = TimeSpan.FromSeconds(2);//2秒增加一个敌人 targetTimer.Tick += TargetTimer_Tick;
targetTimer.Interval = TimeSpan.FromSeconds(.1);//0.1秒执行一次
}
/// <summary>
/// 进度条计时器
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void TargetTimer_Tick(object sender, EventArgs e)
{
progressBar.Value += 1;
if (progressBar.Value >= progressBar.Maximum)
{
EndTheGame();
}
} /// <summary>
/// 游戏结束
/// </summary>
#region 游戏结束
private void EndTheGame()
{
if (!playArea.Children.Contains(gameoverText))
{
enemyTimer.Stop();
targetTimer.Stop();
humanCaptured = false;
starbutton.Visibility = Visibility.Visible;
playArea.Children.Add(gameoverText);
}
}
#endregion
/// <summary>
/// 添加敌人的计时器
/// </summary> private void EnemyTimer_Tick(object sender, EventArgs e)
{
AddEnemy();
}
/// <summary>
/// 点击Star开始游戏
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void Starbutton_Click(object sender, RoutedEventArgs e)
{
StarGame(); }
/// <summary>
/// 开始游戏初始化
/// </summary>
private void StarGame()
{
human.IsHitTestVisible = true;
humanCaptured = false;
progressBar.Value = 0;
starbutton.Visibility = Visibility.Collapsed;
playArea.Children.Clear();
playArea.Children.Add(target);
playArea.Children.Add(human);
enemyTimer.Start();
targetTimer.Start();
}
/// <summary>
/// 添加敌人
/// </summary>
private void AddEnemy()
{
ContentControl enemy = new ContentControl();
enemy.Template = Resources["EnemyTemplate"] as ControlTemplate;
AnimateEnemy(enemy, 0, playArea.ActualWidth - 100, "(Canvas.Left)");
AnimateEnemy(enemy, random.Next((int)playArea.ActualHeight - 100), random.Next((int)playArea.ActualHeight - 100), "(Canvas.Top)");
playArea.Children.Add(enemy); enemy.MouseEnter += Enemy_MouseEnter;
}
/// <summary>
/// 鼠标进入敌人
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void Enemy_MouseEnter(object sender, MouseEventArgs e)
{
if (humanCaptured)
{
EndTheGame();
}
}
/// <summary>
/// 动画函数
/// </summary>
/// <param name="enemy"></param>
/// <param name="from"></param>
/// <param name="to"></param>
/// <param name="propertyToAnimate"></param>
private void AnimateEnemy(ContentControl enemy, double from, double to, string propertyToAnimate)
{
Storyboard storyboard = new Storyboard() { AutoReverse = true, RepeatBehavior = RepeatBehavior.Forever };
DoubleAnimation animation = new DoubleAnimation()
{
From = from,
To = to,
Duration = new Duration(TimeSpan.FromSeconds(random.Next(4, 6)))
};
Storyboard.SetTarget(animation, enemy);
Storyboard.SetTargetProperty(animation, new PropertyPath(propertyToAnimate));
storyboard.Children.Add(animation);
storyboard.Begin();
} /// <summary>
/// 人类是否到达目的地的判断
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void Target_MouseEnter(object sender, MouseEventArgs e)
{
if(targetTimer.IsEnabled && humanCaptured)
{
progressBar.Value = 0;
Canvas.SetLeft(target, random.Next(100, (int)playArea.ActualWidth - 100));
Canvas.SetTop(target, random.Next(100, (int)playArea.ActualHeight - 100));
Canvas.SetLeft(human, random.Next(100, (int)playArea.ActualWidth - 100));
Canvas.SetTop(human, random.Next(100, (int)playArea.ActualHeight - 100));
humanCaptured = false;
human.IsHitTestVisible = true; }
}
/// <summary>
/// 鼠标在游戏区域移动
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void PlayArea_MouseMove(object sender, MouseEventArgs e)
{
if (humanCaptured)
{
//获取鼠标相对于palyArea的位置,无需书上的转换这是wpf与windows Store的不同
//对于这个不理解可以把playArea改为null试试看看区别就晓得了
Point pointerProsition = e.GetPosition(playArea); if((Math.Abs(pointerProsition.X-Canvas.GetLeft(human))>human.ActualWidth*3) || (Math.Abs(pointerProsition.Y - Canvas.GetTop(human)) > human.ActualHeight * 3))
{
humanCaptured = false;
human.IsHitTestVisible = true; }
else
{
Canvas.SetLeft(human, pointerProsition.X - human.ActualWidth / 2);
Canvas.SetTop(human, pointerProsition.Y - human.ActualHeight / 2); }
}
}
/// <summary>
/// 鼠标拖着人类离开游戏区域
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void PlayArea_MouseLeave(object sender, MouseEventArgs e)
{
if (humanCaptured)
{
EndTheGame();
}
} /// <summary>
/// 鼠标左键点击人类的事件
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void Human_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
if (enemyTimer.IsEnabled)
{
humanCaptured = true;
human.IsHitTestVisible = false;
//Console.WriteLine("鼠标按下选中状态:" + humanCaptured); }
} }
}

只要努力没有什么困难可以难倒你,加油骚年!

————————————————————————————————Boting_ISME

![在这里插入图片描述](https://img-blog.csdnimg.cn/20191104205328137.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dlaXhpbl80Mzc1MjA3MA==,size_16,color_FFFFFF,t_70#pic_center =300x)

《Head First C#》外星人入侵WPF编写源码的更多相关文章

  1. 通过解读 WPF 触摸源码,分析 WPF 插拔设备触摸失效的问题(问题篇)

    在 .NET Framework 4.7 以前,WPF 程序的触摸处理是基于操作系统组件但又自成一套的,这其实也为其各种各样的触摸失效问题埋下了伏笔.再加上它出现得比较早,触摸失效问题也变得更加难以解 ...

  2. Java开发在线考试系统 使用ssh框架编写源码

    开发工具: Eclipse,  Tomcat,  MySql       1.  登录页面登录功能, 输入用户名与密码, 选择角色, 滑动箭头拉到最右边才可以点击登录       2.  学生角色登录 ...

  3. 2014年4月份第2周51Aspx源码发布详情

    HFC代码转化工具源码  2014-4-8 [VS2010]源码描述:HFC代码转化工具源码 1.主要实现HTML代码转化为C#或者JS代码,为我们平时编码节省时间. 2.把代码复制到面板上,通过右键 ...

  4. TextView 的新特性,Autosizing 到底是如何实现的? | 源码分析

    一.前言 Hi,大家好,我是承香墨影! 前两天聊了一下 Autosizing 的使用,反映还不错.毕竟是这种能解决实际问题的新 Api,确实在需要的时候,用起来会很顺手. 简单回顾一下,Autosiz ...

  5. c#源码如何生成托管代码块

    1.使用编程语言编写源码--->编程语言的编译器(面向Clr)---->生成IL代码和元数据(包含:代码中声名的类和成员 以及所引用的成员) 2.IL就被称之为托管代码,因为有Clr管理者 ...

  6. Spark Streaming updateStateByKey案例实战和内幕源码解密

    本节课程主要分二个部分: 一.Spark Streaming updateStateByKey案例实战二.Spark Streaming updateStateByKey源码解密 第一部分: upda ...

  7. 源码管理--llorch的Visual Studio基本教程(四)

    通用的演示样例说明: 本系列博客仅仅讨论工具的基础,不讨论不论什么语言. 甚至不讨论快捷键:-) 能够用鼠标就完毕本教程 IDE默认指代的是Visual Studio 2013 Community E ...

  8. WPF学习开发客户端软件-任务助手(已上传源码)

    本人纯属WPF新手,布局和WPF的开发水平相当欠缺,从个人来说,还是比较喜欢WPF的,有人说WPF是界面加上WINFORM,我不这样认为,WPF与WINFORM主要的不同在于数据绑定.   这个软件虽 ...

  9. 图片按日期分类和查看程序(WPF开发)(附源码)

    手机方便了我们的生活,可以随时随地拍摄.越来越多的图片堆砌在电脑里.看到杂乱无章的图片,实在感到头痛.手动整理太复杂.基于此,我写了一个小程序,可以将图片按日期整理和查看.按日期查看图片,回忆过去的点 ...

随机推荐

  1. [译]Vulkan教程(22)创建顶点buffer

    [译]Vulkan教程(22)创建顶点buffer Vertex buffer creation 创建顶点buffer Introduction 入门 Buffers in Vulkan are re ...

  2. [译]Vulkan教程(13)图形管道基础之Shader模块

    [译]Vulkan教程(13)图形管道基础之Shader模块 Shader modules Unlike earlier APIs, shader code in Vulkan has to be s ...

  3. 这可能是最漂亮的Spring事务管理详解

    事务概念回顾 什么是事务? 事务是逻辑上的一组操作,要么都执行,要么都不执行. 事物的特性(ACID): 原子性: 事务是最小的执行单位,不允许分割.事务的原子性确保动作要么全部完成,要么完全不起作用 ...

  4. go语言的常量

    Go 语言常量 常量是一个简单值的标识符,在程序运行时,不会被修改的量. 常量中的数据类型只可以是布尔型.数字型(整数型.浮点型和复数)和字符串型. 常量的定义格式: const identifier ...

  5. Java 中 PO 与 VO 的区别

    什么是PO PO(Persistence Object 持久化对象)是直接跟持久层数据库打交道的java Bean (model,entity,bean等叫法都是可以的),里面除了私有的成员变量之外, ...

  6. 我的计划任务 --- 实现市电停电安全关闭群辉,Windows, Linux等设备

    有一次突然停电,我的群辉DS218+ 的一块硬盘出现故障了,让我担心我的数据安全,其实我是有UPS, 不是在线式的,然后就想如何实现停电自动关机呢? 经过半天的了解,其实群辉支持telnet协议,于是 ...

  7. Web前端基础(12):JavaScript(六)

    1. JS中的面向对象 创建对象的几种常用方法: 1.使用Object或对象字面量创建对象 2.工厂模式创建对象 3.构造函数模式创建对象 4.原型模式创建对象 1.1 使用Object或对象字面量创 ...

  8. 教你用Python实现免费蹭WiFi,只要有WiFi的地方,你就不会断网!

    想象一下,程序员没有WIFI会怎样? 程序员没有网络肯定会寸步难行! 但是对于Python程序员来说,只要附近有热点,分分钟就能蹭网成功! 想要WIFI破解,python+字典,这是必少不了的.热点加 ...

  9. 【React Native】react-native之集成支付宝支付、微信支付

    一.在使用支付宝支付.微信支付之前导入桥接好的头文件 github地址:https://github.com/xujianfu/react-native-pay 二.集成支付宝支付流程 RN支付宝需要 ...

  10. Spring 事务 属性 详细

    学习东西要知行合一,如果只是知道理论而没实践过,那么掌握的也不会特别扎实,估计过几天就会忘记,接下来我们一起实践来学习Spring事务的传播属性. 传播属性 传播属性定义的是当一个事务方法碰到另一个事 ...