C#使用迭代器实现文字的动态效果

目录

一、涉及到的知识点

1.GDI+

2.Thread类

3.使用IEnumerable()迭代器

二、实例

1.源码

2.生成效果:


一、涉及到的知识点

1.GDI+

        GDI+主要用于在窗体上绘制各种图形图像。

        GDI+的核心是Graphics类,该类表示GDI+绘图表面,它提供将对象绘制到显示设备的方法。Graphics类封装了绘制直线、曲线、图形、图像和文本的方法,它是进行一切GDI+操作的基础类。

        本实例使用Graphics类的DrawString方法来绘制动态的文字,该方法常用的语法格式如下:

public void DrawString(string s,Font font,Brush brush,PointF point)参数说明
s:要绘制的字符串。
font:定义字符串的文本格式。
brush:确定所绘制文本的颜色和纹理。
point:指定所绘制文本的左上角。

2.Thread类

        运行C#程序时,如果一个任务执行时间过长,会导致程序主窗体处于“假死”状态。为了避免这种情况发生,可以使用Thread类来创建多线程,即每一个线程完成一个功能,这样就可以有效地避免程序出现“假死”现象。

        本例中使用了Thread thread; //定义线程,thread = new Thread()方法、thread.Start()、thread.Interrupt()、Thread.Sleep()方法。

        其中,thread.Abort();  //已经废弃,用thread.Interrupt();代替。   

3.使用IEnumerable()迭代器

        详见本文作者写的其他文章, C#字符串倒序遍历:Reverse() vs for循环 vs IEnumerable迭代器 vs List<T> vs List<T>迭代器 vs IList<T> vs IList<T>迭代器-CSDN博客  https://wenchm.blog.csdn.net/article/details/136120594

二、实例

        为了使界面具有动态效果,可以在界面中实现一些特殊文字的动态效果。使用迭代器遍历文本字符串中的每一个文字,然后使用GDI+技术在窗体上以不同的字体样式依次绘制每一个文字,以便实现文字的动态效果。

1.源码

// 使用迭代器实现文字的动态效果
// 给窗体添加背景图
using System.Resources;namespace _123
{public partial class Form1 : Form{private Panel? panel1;public Form1(){InitializeComponent();BackgroundImage = Properties.Resources.GetObject("bc");BackgroundImageLayout = ImageLayout.Stretch;StartPosition = FormStartPosition.CenterScreen;Load += Form1_Load;}private void Form1_Load(object? sender, EventArgs e){// // panel1// panel1 = new Panel{Location = new Point(321, 12),Name = "panel1",Size = new Size(250, 83),TabIndex = 0};// // Form1// AutoScaleDimensions = new SizeF(7F, 17F);AutoScaleMode = AutoScaleMode.Font;ClientSize = new Size(600, 416);Controls.Add(panel1);Name = "Form1";Text = "使用迭代器实现文字的动态效果";//Graphics Car_Paint = panel1.CreateGraphics();//实例化绘图对象string CartoonString = "编程词典网";            //定义要绘制的动态文字Character character = new();                   //实例化自定义类对象character.CartoonEffect(panel1, CartoonString);//在窗体上显示动态文字}}class Character{Graphics? graphics;                           //定义Graphics对象static readonly int[] FSize = [20, 25, 30];   //设置字体的大小readonly int Str_block = 5;                   //字体间的间隔readonly Font Str_Font = new("宋体", FSize[0], FontStyle.Bold);//定义字体样式readonly Color Str_Color = Color.Orange;      //定义字体颜色float Str_Width = 0;    //获取字符串的位置float Str_Height = 0;float Panel_W = 0;      //获取控件的宽度float Panel_H = 0;      //获取控件的高度Color Panel_C;          //记录控件的背景颜色float Str_Odd_Width = 0;//获取单个文字的宽度Thread? thread;         //定义线程/// <summary>/// 在Panel控件中绘制动画文字/// </summary>/// <param Panel="C_Panel">显示文字的容器控件</param>/// <param string="C_Str">文字字符串</param>public void CartoonEffect(Panel C_Panel, string C_Str){graphics = C_Panel.CreateGraphics();//为控件创建Graphics对象Panel_H = C_Panel.Height;           //获取控件的高度Panel_W = C_Panel.Width;            //获取控件的宽度Panel_C = C_Panel.BackColor;        //获取控件背景颜色GetTextInfo(C_Str);                 //获取文字的大小及位置graphics.FillRectangle(             //用控件背景填充控件new SolidBrush(Panel_C), 0, 0, Panel_W, Panel_H);DrawFullText(C_Str, 0);             //绘制文字//实例化ParameterizedThreadStart委托线程thread = new Thread(new ParameterizedThreadStart(DynamicText!));thread.Start(C_Str);                //传递一个字符串的参数}/// <summary>/// 获取文字的大小及绘制位置/// </summary>/// <param string="C_Str">文字字符串</param>public void GetTextInfo(string C_Str){SizeF TitSize = graphics!.MeasureString(C_Str, Str_Font); //将绘制的字符串进行格式化Str_Width = TitSize.Width;                           //获取字符串的宽度Str_Height = TitSize.Height;                         //获取字符串的高度Str_Odd_Width = Str_Width / C_Str.Length;            //获取单个文字的宽度Str_Width = (Str_Odd_Width + Str_block) * C_Str.Length; //获取文字的宽度Str_Width = (Panel_W - Str_Width) / 2F;              //使文字居中Str_Height = Panel_H - Str_Height;                   //使文字显示在控件底端}/// <summary>/// 绘制全部文字/// </summary>/// <param string="C_Str">绘制的文字字符串</param>public void DrawFullText(string C_Str, int n){float Str_Place = Str_Width;          //单个字符的位置for (int i = 0; i < C_Str.Length; i++)//遍历字符串中的文字{if (i != n)DrawText(C_Str[i].ToString(), Str_Font, Str_Place, Str_Height); //绘制单个文字Str_Place += Str_Odd_Width + Str_block;                             //获取下一个文字的位置}}/// <summary>/// 绘制单个文字/// </summary>/// <param name="C_Odd_Str">单个文字字符串</param>/// <param name="S_Font">文本样式</param>/// <param name="left"></param>/// <param name="top"></param>public void DrawText(string C_Odd_Str, Font S_Font, float left, float top){graphics!.DrawString(C_Odd_Str, S_Font, new SolidBrush(Str_Color), new PointF(left, top));//绘制字符串中单个文字}/// <summary>/// 通过迭代器实现字符串的遍历/// </summary>/// <param string="n">文字字符串</param>/// <returns>返回单个文字</returns>public static IEnumerable<object> Transpose(string n){if (n.Length > 0){foreach (object i in n)yield return i;}}/// <summary>/// 绘制动态文字/// </summary>/// <param string="C_Str">绘制的文字字符串</param>public void DynamicText(Object C_Str){float tem_left = 0;             //获取当前文字的左端位置float tem_top = 0;              //获取当前文字的顶端位置float tem_width = 0;            //获取文字的宽度float tem_high = 0;             //获取文字的高度float tem_place = Str_Width;    //获取起始文字的位置Font Tem_Font = new("黑体", FSize[0], FontStyle.Bold);//定义字体样式int p = 0;                      //记录字符串中文字的索引号int Str_Index = 0;try{foreach (object s in Transpose(C_Str.ToString()!))//遍历字符串{for (int i = 1; i < 5; i++){if (i >= 3)p = Convert.ToInt16(Math.Floor(i / 2F));elsep = i;DrawFullText(C_Str.ToString()!, Str_Index);Tem_Font = new Font("黑体", FSize[p], FontStyle.Bold);//定义字体样式            SizeF TitSize = graphics!.MeasureString(s.ToString(),Str_Font);//将绘制的单个文字进行格式化 tem_width = TitSize.Width;//获取文字的宽度tem_high = TitSize.Height;//获取文字串的高度tem_left = tem_place - (tem_width - Str_Odd_Width) / 2F;//获取文字改变大小后的左端位置       tem_top = Str_Height - (Str_Height - tem_high) / 2F;  //获取文字改变大小后的顶端位置              DrawText(s.ToString()!, Tem_Font, tem_left, tem_top); //绘制单个文字             Thread.Sleep(200);         //待待0.2秒graphics.FillRectangle(new SolidBrush(Panel_C), 0, 0, Panel_W,Panel_H);//清空绘制的文字}tem_place += Str_Odd_Width + Str_block;//计算下一个文字的左端位置                               Str_Index += 1;                 //将索引号定位到下一个文字}DrawFullText(C_Str.ToString()!, -1);//恢复文字的原始绘制样式//实例化ParameterizedThreadStart委托线程thread = new Thread(new ParameterizedThreadStart(DynamicText!));thread.Start(C_Str);                 //传递一个字符串的参数}catch//这里之所以用异常语句,是在关闭窗体时关闭线程{//thread.Abort();   //已经废弃thread!.Interrupt(); //关闭线程}}}
}

2.生成效果:

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/475262.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

My desktop didn‘t come with the Bluetooth.

You didnt turn on the Bluetooth on PC and phone.Turn on it to control your phone. My desktop didnt come with the Bluetooth. 电脑控制手机的时候&#xff0c;电脑蓝牙没打开 电脑蓝牙打开步骤 电脑蓝牙的小图标打开了 手机上可以看到计算机了【Thinkpad-T440p-zwf】 无…

【力扣白嫖日记】1795.每个产品在不同商店的价格

前言 练习sql语句&#xff0c;所有题目来自于力扣&#xff08;https://leetcode.cn/problemset/database/&#xff09;的免费数据库练习题。 今日题目&#xff1a; 1795.每个产品在不同商店的价格 表&#xff1a;Products 列名类型product_idintstore1intstore2intstore3in…

Query Rewrite —— 基于大模型的query扩展改写,召回提升3%-15%

微软的论文 Query2doc: Query Expansion with Large Language Models https://arxiv.org/pdf/2303.07678.pdf 一、生成假设性答案 通过LLM生成query对应的答案。然后将把答案和原始query拼接成新的query&#xff0c;用于检索。例如&#xff1a; 二、如何把答案和原始query进…

美网络安全威胁能力分析报告

获取方式&#xff1a; 链接&#xff1a;https://pan.baidu.com/s/13RypcyEiNyxe9e0_Gt3ZmQ?pwdbjey 提取码&#xff1a;bjey

使用LlamaIndex和ChatGPT的无代码检索增强生成(RAG)

自从ChatGPT和类似的LLM推出以来&#xff0c;出现了大量的RAG工具和库。人们需要了解如何使用LlamaIndex和ChatGPT的无代码RAG。 检索增强生成(RAG)是使用大型语言模型(LLM)的关键工具。RAG使LLM能够将外部文档合并到它们的响应中&#xff0c;从而更紧密地与用户需求保持一致。…

5G——小区搜索流程

小区搜索流程 小区搜索目标&#xff1a;读取到SIB1. 小区搜索流程概述&#xff1a;SIB1在PDSCH信道承载&#xff0c;承载SIB1的信道在哪个位置由PDCCH告诉&#xff0c;而PDCCH的基本信息由MIB告诉&#xff0c;MIB信息由广播信道PBCH广播出去&#xff0c;物理信道解调需要解调…

gmail smtp python发送邮件

1 到邮箱页面 2 已经开启谷歌Gmail邮箱的IMAP服务了&#xff0c;谷歌邮箱机制是IMAP一旦开通&#xff0c;SMTP也就自动开通了&#xff0c;设置里没有没关系&#xff0c;不用管它。 3 到账号设置页面 3.1 设置两步验证 https://www.cnblogs.com/jiyuwu/p/16313476.html 3.2 …

Day4. 文件IO的基本概念和读写

温习&#xff1a; 文件的拷贝&#xff08;单个字符&#xff09;(fgetc/fputc) #include <stdio.h>int main(void) {FILE* fp NULL;FILE* fq NULL;char ch 0;fp fopen("str.txt","r");if (fp NULL){perror("file to fopen!");retur…

Vue+SpringBoot打造生活废品回收系统

目录 一、摘要1.1 项目介绍1.2 项目录屏 二、研究内容三、界面展示3.1 登录注册3.2 资源类型&资源品类模块3.3 回收机构模块3.4 资源求购/出售/交易单模块3.5 客服咨询模块 四、免责说明 一、摘要 1.1 项目介绍 生活废品回收系统是可持续发展的解决方案&#xff0c;旨在鼓…

软件实例分享,家具生产出库管理系统软件教程

软件实例分享&#xff0c;家具生产出库管理系统软件教程 一、前言 以下软件程序教程以 佳易王家具行业生产出库管理系统软件V16.1为例说明 软件文件下载可以点击最下方官网卡片——软件下载——试用版软件下载 销售管理——产品状态查询变更&#xff0c;可以根据生产进度变更…

keep-alive 的简单使用

vue-router 的嵌套与模块化 router 实例中增加 children 属性&#xff0c;形成层级效果。App.vue 中的 router-view 承载的是 router 实例最外层的路由对象&#xff0c;如 /login、/404 等PageHome.vue 中的 router-view 承载的是 children 中的路由对象&#xff0c;如 /home、…

洛谷P1177 排序 题解

#题外话&#xff08;第30篇题解&#xff09;&#xff08;本题为普及-难度&#xff09;&#xff08;万里挑一-不当人做法&#xff09; #先看题目 题目链接https://www.luogu.com.cn/problem/P1177 #思路&#xff08;我打算不当人&#xff09;&#xff08;本题解仅为交流探讨sor…