怎样画一个点? 300分

zzwu 2008-04-13 11:41:38
加精
请问,

怎样在DOS下,用Fortran,Basic,C(TC,MSC),TP等语言,以及在Windows下,
用VF,VB,VC++,V#,Delphi,Java等语言,画一个任意颜色任意分辨率的点?

为了确切,不妨都定为在640*480和1024*768两种分辨率下,各画一个红
颜色的点,和一个橙颜色的点。

请写出语句和完整程序。问题较多,所以共送300分。

...全文
2842 176 打赏 收藏 转发到动态 举报
写回复
用AI写文章
176 条回复
切换为时间正序
请发表友善的回复…
发表回复
静灵紫 2012-05-30
  • 打赏
  • 举报
回复
这么多高手,学习学习
静灵紫 2012-05-30
  • 打赏
  • 举报
回复
这么多高手,学习学习
huhaifengasd 2012-05-28
  • 打赏
  • 举报
回复
呵呵 不需要关注这些 只要了解就行了 ,你能肯定你比前人牛???还有写出来的东西测试这些都很麻烦,一般公司不会需要这些
熊孩子开学喽 2011-01-26
  • 打赏
  • 举报
回复
楼主其实可以仔细翻阅一下各种语言的图形函数库,应该就可以找到你想要的东西了.
只是因为一般教学的入门书籍都不提这个,所以楼主误会了吧
熊孩子开学喽 2011-01-26
  • 打赏
  • 举报
回复
不明白楼主的意思,莫非楼主是想把每种语言的图像库都从画点开始重新实现一次?
imageproc 2011-01-20
  • 打赏
  • 举报
回复
如果你仅仅是要画出一个点,那么我建议你去看书。
如果你的目的是想画一个矢量化的点,希望有高手帮助解决。
peace12211214 2011-01-14
  • 打赏
  • 举报
回复
高人啊!
skywalker_ll 2010-12-11
  • 打赏
  • 举报
回复
看到回帖的动辄“我20年前”、“我31年前”,大汗……都是业界前辈啊,顶礼膜拜!
包括zzwu在内的所讨论的都还软硬件由一个人包办的年代,但现在,已经分为软件、驱动、硬件三层了。我做过linux的驱动,要在lcd画一个点,调用相应寄存器就是了,这就涉及到对lcd硬件底层驱动编写的深入了解。要实现zzwu的要求,必须从最底层到最高层都有所了解才行,但现在搞图形学的大学生,有几个有这种机会全部经历一遍……
都是流水线上的一颗螺丝钉罢了。

最后,向前辈致敬!也希望我在这个行业里,能达到前辈的高度,坚决不当逃兵,不当炮灰!!!
An4Greenhand 2010-12-10
  • 打赏
  • 举报
回复
路过 学习 “钱难挣 这分看来也不好得啊”貌似根本就得不到,怪自己水平哇是吗 ,那还不如提出1+1为啥要=2(数学上)
jerris 2010-12-07
  • 打赏
  • 举报
回复
真是没事找事干,哥们给你发一个完整的d3d画点。我都测试了。



#include <d3d9.h>


//-----------------------------------------------------------------------------
// Desc: 全局变量
//-----------------------------------------------------------------------------
LPDIRECT3D9 g_pD3D = NULL; //Direct3D对象
LPDIRECT3DDEVICE9 g_pd3dDevice = NULL; //Direct3D设备对象
LPDIRECT3DVERTEXBUFFER9 g_pVB = NULL; //顶点缓冲区对象
int g_iType = 1; //图元类型


//-----------------------------------------------------------------------------
// Desc: 顶点结构
//-----------------------------------------------------------------------------
struct CUSTOMVERTEX
{
FLOAT x, y, z, rhw;
};
#define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZRHW)


//-----------------------------------------------------------------------------
// Desc: 初始化Direct3D
//-----------------------------------------------------------------------------
HRESULT InitD3D( HWND hWnd )
{
//创建Direct3D对象, 该对象用于创建Direct3D设备对象
if( NULL == ( g_pD3D = Direct3DCreate9( D3D_SDK_VERSION ) ) )
return E_FAIL;

//设置D3DPRESENT_PARAMETERS结构, 准备创建Direct3D设备对象
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory( &d3dpp, sizeof(d3dpp) );
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;

//创建Direct3D设备对象
if( FAILED( g_pD3D->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp, &g_pd3dDevice ) ) )
return E_FAIL;

//设置剔出模式为不剔出任何面
g_pd3dDevice->SetRenderState(D3DRS_CULLMODE, D3DCULL_NONE);

//设置图元填充模式为线框模式
g_pd3dDevice->SetRenderState(D3DRS_FILLMODE, D3DFILL_WIREFRAME);

return S_OK;
}


//-----------------------------------------------------------------------------
// Desc: 创建并填充顶点缓冲区
//-----------------------------------------------------------------------------
HRESULT InitVB()
{
//顶点数据
CUSTOMVERTEX vertices[] =
{
{ 50.0f, 250.0f, 0.5f, 1.0f,}
};

//创建顶点缓冲区
if( FAILED( g_pd3dDevice->CreateVertexBuffer( 1*sizeof(CUSTOMVERTEX),
0, D3DFVF_CUSTOMVERTEX,
D3DPOOL_DEFAULT, &g_pVB, NULL ) ) )
{
return E_FAIL;
}

//填充顶点缓冲区
VOID* pVertices;
if( FAILED( g_pVB->Lock( 0, sizeof(vertices), (void**)&pVertices, 0 ) ) )
return E_FAIL;
memcpy( pVertices, vertices, sizeof(vertices) );
g_pVB->Unlock();

return S_OK;
}


//-----------------------------------------------------------------------------
// Desc: 释放创建的对象
//------------------------------------------------------------------------------
VOID Cleanup()
{
//释放顶点缓冲区对象
if( g_pVB != NULL )
g_pVB->Release();

//释放Direct3D设备对象
if( g_pd3dDevice != NULL )
g_pd3dDevice->Release();

//释放Direct3D对象
if( g_pD3D != NULL )
g_pD3D->Release();
}


//-----------------------------------------------------------------------------
// Desc: 渲染图形
//-----------------------------------------------------------------------------
VOID Render()
{
//清空后台缓冲区
g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(45, 50, 170), 1.0f, 0 );

//开始在后台缓冲区绘制图形
if( SUCCEEDED( g_pd3dDevice->BeginScene() ) )
{
//在后台缓冲区绘制图形
g_pd3dDevice->SetStreamSource( 0, g_pVB, 0, sizeof(CUSTOMVERTEX) );
g_pd3dDevice->SetFVF( D3DFVF_CUSTOMVERTEX );

//绘制一个点
g_pd3dDevice->DrawPrimitive( D3DPT_POINTLIST, 0, 1 );


//结束在后台缓冲区渲染图形
g_pd3dDevice->EndScene();
}

//将在后台缓冲区绘制的图形提交到前台缓冲区显示
g_pd3dDevice->Present( NULL, NULL, NULL, NULL );
}


//-----------------------------------------------------------------------------
// Desc: 消息处理
//-----------------------------------------------------------------------------
LRESULT WINAPI MsgProc( HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam )
{
return DefWindowProc( hWnd, msg, wParam, lParam );
}


//-----------------------------------------------------------------------------
// Desc: 入口函数
//-----------------------------------------------------------------------------
INT WINAPI WinMain( HINSTANCE hInst, HINSTANCE, LPSTR, INT )
{
//注册窗口类
WNDCLASSEX wc = { sizeof(WNDCLASSEX), CS_CLASSDC, MsgProc, 0L, 0L,
GetModuleHandle(NULL), NULL, NULL, NULL, NULL,
L"ClassName", NULL };
RegisterClassEx( &wc );

//创建窗口
HWND hWnd = CreateWindow( L"ClassName", L"基本图元",
WS_OVERLAPPEDWINDOW, 100, 100, 600, 300,
GetDesktopWindow(), NULL, wc.hInstance, NULL );

//初始化Direct3D
if( SUCCEEDED( InitD3D( hWnd ) ) )
{
//创建并填充顶点缓冲区
if( SUCCEEDED( InitVB() ) )
{
//显示窗口
ShowWindow( hWnd, SW_SHOWDEFAULT );
UpdateWindow( hWnd );

//进入消息循环
MSG msg;
ZeroMemory( &msg, sizeof(msg) );
while( msg.message!=WM_QUIT )
{
if( PeekMessage( &msg, NULL, 0U, 0U, PM_REMOVE ) )
{
TranslateMessage( &msg );
DispatchMessage( &msg );
}
else
{
Render(); //渲染图形
}
}
}
}

UnregisterClass( L"ClassName", wc.hInstance );
return 0;
}


CyberLogix 2010-12-06
  • 打赏
  • 举报
回复
这个东西深入一下就是图形学的基础问题了,呵呵!
zhoujk 2010-12-03
  • 打赏
  • 举报
回复
因为量变会引起质变,画一个点和画100万个点有本质的区别。当年学图像时,使用 GetPixel 和 SetPixel 即可,也感觉没什么问题,后来需要输出一张图的时候,才发现慢得要死,一秒钟大概只能画几百个点。不得不花了几天时间来研究通过操作内存来读写图像的方法。
Viskag 2010-12-03
  • 打赏
  • 举报
回复
不知道回帖有没有分数的
zhulianbaoyhl73 2010-12-03
  • 打赏
  • 举报
回复
顶 关注
寻开心 2010-02-23
  • 打赏
  • 举报
回复
硬件都在按照摩尔定律快速的增强

但优化依然是一个古老而时髦的话题, 只要你是图形学尤其是三维图形学的爱好者,你就不能不去时刻想它
图形学当中一直都在追求更快的速度,更快的最好办法就是什么都不画,尽可能的减少数据的交换
因为制约的瓶颈是pc的冯。诺依曼架构的设计问题---总线的分时共享,导致数据交换速度的障碍
有兴趣的大家可以计算一下,屏幕多少像素,一秒钟刷25帧要多少数据, 总线传递这些数据更新的时候,要占用多少时间,就清楚了

支持这个帖子后,再开个画线, 和再开个三角形填充的同样话题
寻开心 2010-02-23
  • 打赏
  • 举报
回复
哈哈, zzwu,还在这儿那, 你坚持的可真长啊, 我有2年多没有来了, :)
这个问题让我回想到当年(90年代出)的dos下的图形编程了, cc, 好怀念哦!

显存和内存有个“交换区”, 在dos下,你是可以直接写到, 在windows下不能

在dos下16位系统 0xb800:0000 好像是这个地址,老了,记忆不清楚了, 对应的放置的是文字屏幕下的字幕,相邻连个单元一个是字幕的ascii代码,一个是颜色, 当年最好的办法就是直接在这个地址写文字和该颜色, 比任何标准的io函数都快几十倍

图片区是0xc000:0000, 通过dos的int 13调用来更改分辨率
在不同分辨率下, 每个像素点占用的大小不一样,比如2色的时候, 每个bit就是一个点,256色的时候1个字节一个,保存的是调色板的索引, 16色或者24位色,每个像素2-3个字节
从屏幕的左上角0,0开始对应0xc000000, 分辨率和颜色深度决定了连续接下来多少字节对应一行

画点的本质就是向这个区域写数据,根据不同的分辨率和颜色深度写不同的数据进去

显示器根据这个内存交换区的数据,来解释这个点子屏幕上到底是什么
什么时候写,还要考虑垂直回扫时间......

当显示卡的显存较多的时候,还可以通过int 13来更换不同的显示页,还可翻页等

windows 系统进入32位的实模式时代, 这个dos下的方式就不能用了
禁止了用户直接访问内存,都用虚拟地址来处理了
但是基本原理还是一样的, 无非是中间多了一层GDI的管理
通过GDI调用底层的厂家的显示驱动来实现相应的功能

好怀念dos啊, 那个时候, 俺可以按照想法做电脑的完完全全的所有的控制!

了解世界的本源是很有必要的, 强烈支持zzwu的科普工作
zhoujk 2010-02-19
  • 打赏
  • 举报
回复
我想在这个贴中,楼主的一个考虑是关于运行效率。无法接近低层,则对代码的优化就很难实现。OS提供的封装让程序员不用接近底层,在提高开发效率的同时降低了运行效率。例如,每个函数的调用都需要一定的时间和空间成本。但是为了降低程序和开发和维护难度,仍然得用。这种封装得到了软件业界的认同,除了极个别的应用。事实上,从大的时间跨度来看,封装的程度是越来越高
如果要运行效率,汇编或直接操作机器码。但是每种硬件的操作都是不同的。。。
如果回到DOS时代,每种软件都对硬件(显卡,鼠标,打印机)需要编写驱动的话,那么在开发效降低的同时,运行效率真的能够提升吗?我们写的这些驱动,能够经得起最严格的测试吗?
这是个上一时代的问题,大概很多当年玩得转的老手已经把这些技术忘了,毕竟时代在进步
zzwu 2010-02-18
  • 打赏
  • 举报
回复
引用 157 楼 sfp_801 的回复:
我只想用汇编语言和c语言在一台裸机上画一个圆圈,我该怎么做?


有趣的问题!我31年前曾编过这个程序,化了我不少心血! 也遇到过一个很重要,但可惜没有记录下来奇迹!




对我有用[0] 丢个板砖[0] 引用 举报 管理 TOP
zzwu 2010-02-18
  • 打赏
  • 举报
回复
引用 156 楼 liuzf05 的回复:
哇,大家还在讨论呢!晚上把我知道的东西发上来供大家批评批评


有趣的问题! 我31年前曾编过这个程序, 化了我不少心血, 也遇到过一个很重要,但可惜没有记录下来奇迹!

liuzf05 2010-02-08
  • 打赏
  • 举报
回复
哇,大家还在讨论呢!晚上把我知道的东西发上来供大家批评批评
加载更多回复(154)

4,445

社区成员

发帖
与我相关
我的任务
社区描述
图形图像/机器视觉
社区管理员
  • 机器视觉
  • 迪菲赫尔曼
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧