返回列表 发帖

[其他] EasyIFS分形学演示,命令行版

EasyIFS分形学演示工具是ZH@EASYX.CN用easyx库写的作品,体积比较大,并且不属于控制台程序,我用GDI库改写了该工具,使其可以在批处理中批量调用,并修复原版个别漏洞。体积也由112KB缩小到13KB。
下载附件:http://bcn.bathome.net/s/tool/index.html?key=EasyIFS
图片均为外链图
/*
CONSOLE FRACTAL IFS, AUTHOR: ZH@EASYX.CN, MODIFYED BY HAPPY.
EASYIFS.EXE
*/
#include    <string>
#include    <vector>
#include   <stdio.h>
#include <windows.h>
#include   <conio.h>
#include    <time.h>
#include      <io.h>
using namespace std;
// 对VC6.0、VS2010、GCC作兼容性编译
#if defined (__GNUC__) || (_MSC_VER == 1200)
extern "C" HWND WINAPI GetConsoleWindow();
#endif
// 宏名变量定义
#define F_EXIST 4
#define E_WITH  640
#define E_HIGH  480
// 定义帮助说明
#define HELP_INFORMATION "\
Usage: easyifs [file]\n\
\n\
    The probability of requiring each formula and equ 1\n\
    IFS configuration file:\n\
\n\
    [Main]\n\
    name = IFS name\n\
    iterLimit = number of iterations\n\
    color = drawing color\n\
    minX = the lower limit of x\n\
    maxX = the upper limit of x\n\
    minY = the lower limit of y\n\
    maxY = the upper limit of y\n\
    condition = the number of formulas\n\
    [Conditionx]\n\
    p = probability\n"
// IFS 全局参数
struct MAIN
{
string name;             // ifs 名称
int iterLimit;           // 迭代次数
int color;               // 绘图颜色
double scale;            // 相对绘图窗口的缩放比例
int offsetX, offsetY;    // 相对绘图窗口的偏移量
};
// 每个IFS公式的参数
struct IFS
{
int p;                   // 概率
double a, b, c, d, e, f; // IFS 公式参数
};
// 全局变量
MAIN g_main;
vector<IFS> g_ifs;
// 从配置文件中获取 double 类型数据
double GetPrivateProfileDouble(LPCTSTR lpAppName, LPCTSTR lpKeyName, double fDefault, LPCTSTR lpFileName)
{
TCHAR d[50];
GetPrivateProfileString(lpAppName, lpKeyName, NULL, d, 50, lpFileName);
return (d[0]!=0)?atof(d):fDefault;
}
// 根据配置文件初始化 IFS 系统
int initargs(int argc, char** argv)
{
// 如果未指定参数,显示帮助信息
if (argc <= 1)
{
fprintf(stdout, HELP_INFORMATION);
exit(1);
}
// 定义变量
double ix, ax, iy, ay, sx, sy;
// 配置文件的文件名
char tmpFpath[MAX_PATH*2];
if(strrchr(argv[1], ':')==NULL)
{
strcpy(tmpFpath, ".\\");
strcat(tmpFpath, argv[1]);
}
else
{
strcpy(tmpFpath, argv[1]);
}
char* filename=tmpFpath;
// 如果参数指定的文件不存在或禁止访问,退出系统
if (_access(filename, F_EXIST) != 0)
{
fprintf(stdout, "The file \"%s\" does not exist or is disabled.\n", argv[1]);
exit(2);
}
// 获取 IFS 名称
char tmpName[MAX_PATH*2];
GetPrivateProfileStringA("main", "name", "noname", tmpName, 50, filename);
g_main.name = tmpName;
// 获取迭代次数
g_main.iterLimit = GetPrivateProfileIntA("main", "iterLimit", 0, filename);
// 获取绘图颜色
g_main.color = GetPrivateProfileIntA("main", "color", 0xff00, filename);
// 获取 x 方向上的缩放比例
ix = GetPrivateProfileDouble("main", "minX", 0, filename);
ax = GetPrivateProfileDouble("main", "maxX", 0, filename);
sx = E_WITH / (ax - ix);
// 获取 y 方向上的缩放比例
iy = GetPrivateProfileDouble("main", "minY", 0, filename);
ay = GetPrivateProfileDouble("main", "maxY", 0, filename);
sy = E_HIGH / (ay - iy);
// 根据绘图窗口尺寸,确定恰当的缩放比例及偏移量
if (sx > sy)
{
g_main.scale = sy;
g_main.offsetX = (int)(-ix * g_main.scale + (E_WITH - (ax - ix) * g_main.scale) / 2);
g_main.offsetY = (int)(-iy * g_main.scale);
}
else
{
g_main.scale = sx;
g_main.offsetX = (int)(-ix * g_main.scale);
g_main.offsetY = (int)(-iy * g_main.scale + (E_HIGH - (ay - iy) * g_main.scale) / 2);
}
// 获取公式数量
int n;
n = GetPrivateProfileIntA("main", "condition", 0, filename);
// 获取每一个公式的常数项及概率
IFS ifs;
int sump = 0;
char app[] = "condition?";
for(int i=0; i<n; i++)
{
app[9] = ('1' + i);
ifs.a = GetPrivateProfileDouble(app, "a", 0, filename);
ifs.b = GetPrivateProfileDouble(app, "b", 0, filename);
ifs.c = GetPrivateProfileDouble(app, "c", 0, filename);
ifs.d = GetPrivateProfileDouble(app, "d", 0, filename);
ifs.e = GetPrivateProfileDouble(app, "e", 0, filename);
ifs.f = GetPrivateProfileDouble(app, "f", 0, filename);
ifs.p = int(GetPrivateProfileDouble(app, "p", 0, filename) * 1000000 + 0.5);
ifs.p += sump;
sump = ifs.p;
g_ifs.push_back(ifs);
}
// 如果各公式的概率和不等于 1,返回错误信息
if (sump != 1000000)
{
fprintf(stdout, "IFS configuration file in the probability of the formula and not equal to 1, please check the configuration file.\n");
exit(3);
}
return 0;
}
// 主函数
int main(int argc, char* argv[])
{
// 初始化IFS配置
initargs(argc, argv);
srand(unsigned(time(NULL)));
// 初始化图形窗口
HWND hCMD=GetConsoleWindow();
//刷新窗口
InvalidateRect(hCMD, NULL, TRUE);
HDC  hDC=GetDC(hCMD);
// 创建变量
double x = 0, y = 0, tx;
int p, k;
//设置背景透明
//SetBkMode(hDC,TRANSPARENT);
//设置字体颜色
//SetTextColor(hDC, RGB(255,255,255));
// 显示名称
//TextOutA(hDC, 0,0, g_main.name.c_str(), strlen(g_main.name.c_str()));
// 迭代求解
for(int i=0; i<g_main.iterLimit; i++)
{
// 生成概率
p = int(double(rand()) / RAND_MAX * 1000000 + 0.5);
// 根据概率获取选用的公式 k
for(k=0; k< (int)g_ifs.size(); k++)
if (p <= g_ifs[k].p) break;
// 根据公式 k 迭代
tx = g_ifs[k].a * x + g_ifs[k].b * y + g_ifs[k].e;
y  = g_ifs[k].c * x + g_ifs[k].d * y + g_ifs[k].f;
x  = tx;
// 画点(转换到屏幕坐标系)
SetPixel(hDC, int(x * g_main.scale) + g_main.offsetX, E_HIGH - (int(y * g_main.scale) + g_main.offsetY),  g_main.color);
}
return 0;
}COPY
1

评分人数

    • 老刘1号: 沉迷于绘图无法自拔的Happy兄技术 + 1

返回列表