Mac OS Cocoa:在画布上绘制一个简单的像素

Rom*_*man 11 macos cocoa pixel objective-c nsimageview

我希望我能找到答案.我搜索并搜索过,但答案不对.这是我的情况:

在Mac OS Cocoa应用程序中,我想在我的应用程序窗口的专用区域上绘制一个像素(实际上是几个像素).我想,NSImageView放在那里会更好(我用IB做了这个并将插座连接到我的应用代表)然后用它代替我的NSWindow.

我怎么能这样做呢?Mac OS似乎提供NSBezierPath了最基本的绘图工具 - 这是真的吗?这对我来说是完全令人震惊的.我来自Windows编程的悠久历史,并且通常在画布上绘制像素是最简单的事情.

我不想使用OpenGL,我不确定Quartz参与的程度如何.

我想要的只是帮助我如何在真正的Objective-C/Cocoa中实现这个伪代码:

imageObj.drawPixel(10,10,blackColor);
Run Code Online (Sandbox Code Playgroud)

我很想听听你的回答,我相信这会帮助很多人从Cocoa开始.

谢谢!

Log*_*chu 12

您要求的是以下两种方法之一:

NSBitmapRep setColor:atX:y:更改指定坐标处像素的颜色.

NSBitmapRep setPixel:atX:y:将指定坐标处的接收器像素设置为指定的原始像素值.

请注意,这些在iOS上不可用.在iOS上,似乎这样做的方法是为给定的颜色空间(可能是RGB)创建像素数据的原始缓冲区,用颜色数据填充它(写一点setPixel方法来执行此操作)然后调用CGImageCreate()像这样:

    //Create a raw buffer to hold pixel data which we will fill algorithmically
    NSInteger width = theWidthYouWant;
    NSInteger height = theHeightYouWant;
    NSInteger dataLength = width * height * 4;
    UInt8 *data = (UInt8*)malloc(dataLength * sizeof(UInt8));

    //Fill pixel buffer with color data
    for (int j=0; j<height; j++) {
        for (int i=0; i<width; i++) {

            //Here I'm just filling every pixel with red
            float red   = 1.0f;
            float green = 0.0f;
            float blue  = 0.0f;
            float alpha = 1.0f;

            int index = 4*(i+j*width);
            data[index]  =255*red;
            data[++index]=255*green;
            data[++index]=255*blue;
            data[++index]=255*alpha;

        }
    }

    // Create a CGImage with the pixel data
    CGDataProviderRef provider = CGDataProviderCreateWithData(NULL, data, dataLength, NULL);
    CGColorSpaceRef colorspace = CGColorSpaceCreateDeviceRGB();
    CGImageRef image = CGImageCreate(width, height, 8, 32, width * 4, colorspace, kCGBitmapByteOrder32Big | kCGImageAlphaPremultipliedLast,

                            provider, NULL, true, kCGRenderingIntentDefault);

    //Clean up
    CGColorSpaceRelease(colorspace);
    CGDataProviderRelease(provider);
    // Don't forget to free(data) when you are done with the CGImage
Run Code Online (Sandbox Code Playgroud)

最后,您可能想要操作已加载到CGImage中的图像中的像素.在Apple Technical Q&A中有一个标题为QA1509的示例代码,用于从CGImage对象获取像素数据.


ben*_*ado 9

Cocoa的低级绘图API是Core Graphics(Quartz).您将获得绘图上下文并发出命令以绘制到该上下文.API被设计为与设备无关(您在打印时使用相同的命令绘制到屏幕上,就像在纸上绘图一样).因此,没有用于填充单个像素的命令,因为在纸上没有诸如像素之类的东西.即使在屏幕上,您的视图也可能以某种方式进行了转换,因此单个点不会映射到单个设备像素.

如果要绘制单个像素,则需要指定一个单个像素大小的矩形,然后将其填入.对于(x,y)处的像素,您需要一个原点为(x-的矩形) 0.5,y-0.5)和(1,1)的大小.

您可以使用NSBezierPath执行此操作,或者您可以从中获取Core Graphics上下文(CGContextRef)[[NSGraphicsContext currentContext] graphicsPort]并使用类似的函数CGContextFillRect().

如果要绘制大量像素,这显然不会很快; 这不是API的目的.如果这是您需要做的,请考虑创建一个缓冲区,malloc并将像素数据写入其中,然后使用Core Graphics将其转换为CGImageRef,可以将其绘制到屏幕上.


Ser*_*gio -11

NSBezierPath 是 Cocoa 中唯一可用于绘制最原始形状和许多复杂形状的工具。您可以在这里找到详细说明: http://developer.apple.com/library/mac/#documentation/Cocoa/Conceptual/CocoaDrawingGuide/Paths/Paths.html%23//apple_ref/doc/uid/TP40003290-CH206-BBCHFJJG http://en.wikibooks.org/wiki/Programming_Mac_OS_X_with_Cocoa_for_Beginners/Graphics__-_Drawing_with_Quartz