教孩子用Pygame Zero编程

你怎样才能激发一个孩子对编程和电脑的兴趣?作为一名软件开发人员和两个孩子的父亲,我经常思考这个问题。一个拥有软件技能的人在现代社会会有很大的优势,所以我想让我的孩子们为他们的未来做好准备。

在我家,我们一起玩电子游戏。我的孩子们(6岁和4岁)看着我玩《超级马里奥世界》和《塞尔达传说:回到过去》等经典游戏。他们喜欢花时间和爸爸在一起,也很喜欢玩电子游戏。当我想到我六岁的儿子可能会喜欢编程时,利用电子游戏作为进入计算领域的渠道是一个非常自然的想法。

我最近才开始探索游戏开发,所以和我儿子一起开发游戏似乎是个不错的主意。当我问他是否想要创造一款游戏时,他当然会说“YES!”

是否学习Scratch编程?

一旦我确定了他的兴趣,是时候弄清楚该做什么了。过去,我们尝试过ScratchJr。ScratchJr使用图形界面和UI块来组合一组操作。ScratchJr附带的工具包括循环、计数和许多属于软件开发的其他核心内容。我观察儿子的经验表明,ScratchJr与编程的距离太远了。

起初,我的儿子会把小角色拖到屏幕上,让他们跳上跳下,或者从一边移动到另一边。后来,他的剧本变成了使用这个应用程序作为美化的绘画程序。他会录下自己的声音片段,改变角色的颜色,并以无数种其他方式搅乱场景。我热爱艺术,对他追求艺术兴趣完全没有异议,但是ScratchJr并没有教授编程技能。我不知道这些动作是不是太局限了,或者他没有把这个工具看作是一种创造互动的工具。

当我考虑我们的游戏项目时,ScratchJr的经验使我排除了Scratch(构建块编程的更高级版本)。我还听了一段很棒的对话,帮助我强化了自己的信念,即Scratch不是一条必经之路。在这一集中,迈克尔采访了尼古拉斯·托勒维(Nicolas Tollervey),谈了如何使用BBC micro:bit教授Python。

尼古拉斯提出了一个让我印象深刻的观点。作为一名训练有素的音乐家,他指出,音乐教学是用真正的乐器来教孩子们的(尽管要小一些,以适应孩子们的尺寸)。孩子们用真正的乐器来培养音乐技能,当孩子在成长过程中得到一个更大版本的乐器时,这些技能是可以直接转移的。我们知道这个系统是有效的,因为几百年来孩子们就是这样学习乐器的。他的观点是:如果音乐教学演示了如何教一个孩子一种复杂的技能,比如演奏乐器,为什么我们不应该把这种策略应用到编程教学中呢?

在那一刻,我开始相信,我能为我的儿子提供的最好的服务就是用一种具备他所需要的所有特性的编程语言来教他,Python是我显而易见的选择。

Mu editor

关于这个项目,我还有很多方面需要弄清楚。对于一个还不知道如何打字的孩子来说,正确的用户界面是什么?

值得庆幸的是,在“ Talk Python To Me”一集中有更多的金币。尼古拉斯还主要负责Mu editor(链接:https://codewith.mu/)。

Mu是一个专注于为初学者运行Python的编辑器。Mu对于初学者来说非常棒。以下是一些亮点:

1)包含Python,因此无需额外安装!

2)预装了许多受欢迎的软件包,例如requests,matplotlib和pyserial等。

3)有一种模式可以直接与Adafruit的CircuitPython一起使用,以在Python中使用硬件和微控制器。

4)使用预先安装的Pygame Zero(链接:https://pygame-zero.readthedocs.io/en/stable/)可以进行游戏开发。

最后一个亮点是我选择为儿子使用Mu的明确原因。

Pygame Zero对比Pygame

Pygame Zero是制作视频游戏的工具。它是独立的,但与Pygame有关,Pygame是一个长期存在的Python项目,可让您使用Python构建(主要是2D游戏)。

Pygame Zero和Pygame之间的差异与目标受众有关。我认为Pygame Zero文档很好地说明了他们的项目目标:

[Pygame Zero]专用于教育,因此教师无需讲解Pygame API或编写事件循环就可以教授基本编程。

我在这篇文章的开头提到,我也在学习如何编写游戏。在我个人对游戏开发的探索中,Pygame是我编写游戏的首选。(说实话,我一开始是喜欢用Lua做实验,并制作了一个Pong克隆版,但我的结论是Lua不适合我。)

根据我的经验,Pygame对初学者来说不是很友好。从几年前开始,我已经学到了很多关于游戏开发的知识。当我今天看Pygame时,它更像是一个游戏库而不是游戏引擎。所有的部件都已经准备好了,但是你必须自己将所有的部件连接起来。长期游戏开发人员可能喜欢这种灵活性,但对于新开发人员来说,这种灵活性是无法承受的。对于一个六岁的孩子来说,这几乎是不可能的。

当我试用Pygame Zero时,我惊讶地发现这种体验有多么不同。Pygame Zero更像是一个游戏引擎。在Pygame中必须自己处理的公共部分是预先连接在Pygame Zero中的。这极大地降低了进入门槛,但牺牲了灵活性。这绝对是教学的正确权衡。

我们做了什么

在所有这些研究之后,我们在Pygame Zero中创造了我们的第一个游戏。让我们看看我儿子的代码,然后探究他和我在这个过程中学习到的东西。

首先,这是他的第一个游戏。

slimearm = Actor('alien')
slimearm.topright = 0, 10

WIDTH = 712
HEIGHT = 508

def draw():
    screen.fill((240, 6, 253))
    slimearm.draw()

def update():
    slimearm.left += 2
    if slimearm.left > WIDTH:
        slimearm.right = 0

def on_mouse_down(pos):
    if slimearm.collidepoint(pos):
        set_alien_hurt()
    else:
        print("you missed me!")

def set_alien_hurt():
    print("Eek!")
    sounds.eep.play()
    slimearm.image = 'alien_hurt'
    clock.schedule_unique(set_alien_normal, 1.0)

def set_alien_normal():
    slimearm.image = 'alien'

这是游戏运行的截图:

他的整个游戏包含29行代码,包括空行。在这29行代码中,他学会了大量的东西。另外,为了证明它的正确性,这个游戏是PyGameZero简介中所列游戏的修改版。

他学到了什么?

如果你已经写了很长一段时间的代码,你很容易忘记那些在编程中很难或者很奇怪的事情。

命名事物

在游戏的第一行,我儿子必须处理变量。

slimearm = Actor('alien')

变量(特别是对于那些没有做过代数的人)是一个非常奇怪的概念。我解释了变量是如何作为其他东西的名称的,以及变量的名称可以是我们想要的任何名称。因为我们的程序花了很多个周末来完成,所以我们每次都要重新访问变量的概念。最后,我发现最好的方法是建议我们把文档中的alien名称改为其他名称。这样,他选择的slimearm就诞生了。

使用不同的变量名有助于让他拥有自己编写的代码的所有权。我们讨论了他如何使用slimearm的名字,而不是从文档页面上看到的名字。

可变性(Mutability)

我儿子还学会了软件的延展性。Pygame Zero使得这一点非常容易展示。

WIDTH = 712
HEIGHT = 508

设置游戏的窗口大小只需要更改WIDTH和HEIGHT。我儿子会:

1)摆弄数字。

2)启动游戏查看结果,然后再次停止。

3)选择一些疯狂的数值。

4)启动游戏以查看古怪的窗口大小。

5)重复,直到他高兴为止。

程序功能和学习效果

我认为电子游戏和教学节目一样神奇的地方在于它们所产生的学习效果。

游戏真的很棒,由于向我们展示了我们的代码正在做的事情,它们带来了很多满足感。

当我使用绘图功能时,我的儿子看到了他所看到的东西:计算机正在执行他所写的东西!

def draw():
    screen.fill((240, 6, 253))
    slimearm.draw()

这个draw函数没有返回语句。每次调用它时,由于slimearm的状态不同,结果也会不同。

在我家里,我们经常玩Arduino电路,这样我的孩子们就知道什么是LED了,我儿子也知道LED里面有红色、绿色和蓝色的灯。我不费心解释元组,但我告诉他要填充的三个数字是RGB。我们启动了Chrome DevTools,启动了一个颜色选择器,他拖来拖去,直到我们找到了“完美”的颜色。

状态和时间

在我们看到slimearm的效果之前。在绘制函数中,我们需要更新外星人的状态来推进它的位置。

def update():
    slimearm.left += 2
    if slimearm.left > WIDTH:
        slimearm.right = 0

当我到达这个阶段时,我必须找到一种方法来解释Pygame Zero如何在绘制和更新之间交替进行以使游戏运行。这是“更新方法模式”的一个示例。

我用幻灯片的想法来说明这个概念。事后看来,这可能不是我儿子2012年出生以来最好的比喻。对于大多数视频制作来说,我们已经进入数字时代,因此电影非常罕见。

在我解释了胶片是如何工作的之后,我的儿子开始接受将画面作为独立图像画在屏幕上的想法。我们讨论了更新是如何在帧之间进行的以及如何导致帧之间的不同。他似乎理解了这个概念,但是我们必须探索坐标和(x, y)对,以及更多他还没有学习过的代数概念!

所以,我又从头开始了。我所能想到的解释事物在二维坐标空间中如何工作的最好方法是使用纸质原型。

我们的纸原型是一个非常有用的视觉工具。在原型中,我创建了一个游戏窗口和我们的外星人角色,我将其标记为slimearm以匹配变量名。用这两张不同的纸,我的儿子可以用一种非常直观的方式看到人物是如何移动的。通过对幻灯概念的固定,我们迭代了游戏中的每一帧。因为他能指出不同的部分,比如在更新方法中前进的左边缘,他就能理解电脑是如何改变外星人的位置的。

这些标签还帮助他掌握了条件逻辑。通过在每个循环中询问“ slimearm的左边缘是否比窗口宽度更远?”,可以清楚地知道何时应将外星人重新定位在左侧以及精灵的哪个边缘。

与游戏互动

如果你不能在游戏中做些什么,那么游戏就不是真正的游戏。这个游戏的目的是试着点击外星人。如果你点击它,你会听到一个小声音,看到外星人暂时变成了一个受伤的形象。

def on_mouse_down(pos):
    if slimearm.collidepoint(pos):
        set_alien_hurt()
    else:
        print("you missed me!")

我们从事件的概念开始。作为一个数字原住民,我的儿子在思考触摸屏幕等行为时没有遇到任何困难。理解“鼠标下拉”事件需要一些解释,但是我们使用可靠的print函数来快速说明这个概念。

Mu的游戏模式有一个内置的控制台,你可以在游戏运行时在编辑器中看到它。我们的第一个版本的函数看起来更像这样:

def on_mouse_down(pos):
    print('You clicked!')

即使是这样简单的互动也足以让我的儿子兴奋起来。我试着跟他说点什么,但他会打开游戏,然后四处点击,看到一连串的“You clicked!”消息显示在控制台上。事实证明,低技术反馈足以让孩子们兴奋!

当我们升级到完整功能时,我不得不解释碰撞。由于现实世界的相似性,碰撞的想法是很自然的。

def set_alien_hurt():
    print("Eek!")
    sounds.eep.play()
    slimearm.image = 'alien_hurt'
    clock.schedule_unique(set_alien_normal, 1.0)

当我们使用set_alien_hurt函数时,我们实际上是通过添加声音效果和更改精灵图像来处理游戏的效果。其中最棘手的部分是解释计算机时钟和这行代码的目的:

    clock.schedule_unique(set_alien_normal, 1.0)

我仍然不确定他是否理解了这个概念。坦白地说,我们几乎让所有东西都工作了,所以他对添加更多代码的兴趣很快就消退了。schedule_unique是一段具有挑战性的代码。你需要理解函数是可以像变量一样传递的东西。您还需要考虑set_alien_normal将在将来某个时候调用,而不是由您编写的代码调用。我没有在代码中详细讨论这一点,因为我们显然已经达到了他的好奇心的极限。

这使我们结束了他的游戏代码。我儿子涵盖了如下编码概念:

  • Naming(命名)
  • Mutability(可变性)
  • Functions and side effects(功能及效果)
  • State and time(状态和时间)
  • Interaction(交互)

对于几乎所有程序员来说,这都是一个非常棒的主题列表!

我学到了什么?

让我们以我作为老师的一些个人经验来结束这个话题。有些教训让我想起了我所知道的事情,但有些是新的教训。我有一个孩子,他刚刚开始独立自主地学习,所以我正在学习如何最好地帮助他。

重复,重复,重复

对于我们大多数人来说,我们的大脑不会在第一次接触到概念之后就被锁定。我们需要反复体验事物,才能让概念深入人心。当我的儿子与变量作斗争时,我看到了这一点。每当他回忆变量时,我必须提醒他这些变量的作用。

如果我对这种行为没有心理准备,我很容易就会生气。因为我已经研究变量很多年了,我已经远离了第一次接触,几乎不记得那是什么样子了。当我觉得他没有掌握概念的时候,锻炼耐心是我的解决办法。

反馈是至关重要的

我观察到我的儿子最感兴趣的是什么时候电脑会根据他的输入做一些事情。无论是显示颜色、显示文本、发出声音,还是其他任何事情,他都会在这些反馈的时刻感到高兴。这也给我带来了满足感。当你的孩子抓住一个想法时,看到他们脸上的喜悦是作为父母的回报之一。

使用道具

孩子们学习的方式多种多样。当我用文字解释一些想法时,切换到纸质模型极大地改善了我们两人的教育体验。这不仅是一个我们可以一起快速完成的工作,而且它是这个过程中的一个极好的助手。

认识到限制

我认为我的儿子现在能够自己制作一款游戏吗?当然不是。我必须记住,在我们创造这款游戏的过程中,他能够保留多少是有限制的。我没有期望他在我们完成后会成为一个出色的程序员。这意味着,当我们遇到一些较难的概念时,我会稍微推动一下,让他拓展自己的思维,但当他还没有为某个想法做好准备时,我就会退后。

庆祝!

制作游戏带有一定的内在奖励,但我也希望我的儿子能看到一个非常明确的外在奖励。学习编程是一件困难的事情,而制作一些有用的东西(即使它来自于文档教程)是一件值得庆祝的壮举。

有多少孩子设法制作自己的电子游戏? 我敢肯定,这个数字很小。因此,我竭尽全力摆脱平常的坚忍态度,与儿子庆祝。在这样做的过程中,他会欣赏与一个了解该项目并关心他的人所取得的成就。

接下来怎么办呢?

没过多久,他就开始对我们一起创造的下一款游戏有了自己的想法。这款游戏仍处于计划和构思阶段,但他很高兴能参与其中。

这正是我所希望的结果。我儿子现在把编程看作是制造东西的工具。我认为这个世界需要更多的创造者。

感谢你的阅读!

六一编程网

Next Post

教孩子们编程:2020年最佳免费编程网站

周三 7月 1 , 2020
在过去的十年里,我们的笔记本电脑和智能手机已经成为我们生活中最重要的物品。智能设备的使用呈指数级增长 […]