iOS_26PopoverController简单使用

最终效果图:

UIImage分类,Point2Color:

//
//  UIImage+Point2Color.h
//  26_popOverCtrl
//
//  Created by beyond on 14-8-31.
//  Copyright (c) 2014年 com.beyond. All rights reserved.
//

#import <UIKit/UIKit.h>

@interface UIImage (Point2Color)
// 传入 一个点坐标,返回图片上该点的颜色对象
- (UIColor *)colorFromPoint:(CGPoint)point;
@end
//
//  UIImage+Point2Color.m
//  26_popOverCtrl
//
//  Created by beyond on 14-8-31.
//  Copyright (c) 2014年 com.beyond. All rights reserved.
//  分类,传入一个point,获取该点的颜色

#import "UIImage+Point2Color.h"

@implementation UIImage (Point2Color)

// 传入 一个点坐标,返回图片上该点的颜色对象
// 将图片写入内存,再依据【点】中取颜色
- (UIColor *)colorFromPoint:(CGPoint)point
{
	UIColor *color = nil;
    // 得到取色图片的引用
	CGImageRef inImage = self.CGImage;
    // 调用自定义方法:从_imgView里面的image的引用,创建并返回对应的上下文
	CGContextRef contexRef = [self ARGBBitmapContextFromImage:inImage];
    // 如果创建该图片对应的上下文失败
	if (contexRef == NULL){
        NSLog(@"取色图片--创建对应的上下文失败~");
        return nil;
    }
	// 准备将【取色图片】写入刚才创建出来的上下文
    size_t w = CGImageGetWidth(inImage);
	size_t h = CGImageGetHeight(inImage);
	CGRect rect = {{0,0},{w,h}};
    // 调试输出rect:--{{0, 0}, {225, 250}}

	// 将位图写入(渲染)已经创建好的  上下文工作空间
	CGContextDrawImage(contexRef, rect, inImage);

	// 得到位图上下文 内存数据块的首地址,用指针记住,作为基地址
	unsigned char* dataPoint = CGBitmapContextGetData (contexRef);
    NSLog(@"----首地址,指针%p",dataPoint);
    // ----首地址,指针0x8b3f000
	if (dataPoint != NULL) {
		//offset 即:根据触摸点的xy,定位到位图内存空间中的一个特定像素
        //4 的意思是每一个像素点,占4个字节
        // w是每一行所有点的总数
        // 根据所在行,所在列,算出在内存块中的偏移地址,然后乘以4,因为每一个点在内存中占四个字节
		int offset = 4*((w*round(point.y))+round(point.x));
        // alpha 为内存基地址+偏移地址
		int alpha =  dataPoint[offset];
        // red 为内存基地址+偏移地址+1   其他类似
		int red = dataPoint[offset+1];
		int green = dataPoint[offset+2];
		int blue = dataPoint[offset+3];
        NSLog(@"偏移地址: %i colors: RGBA %i %i %i  %i",offset,red,green,blue,alpha);
        // offset: 150908 colors: RGB A 255 0 254  255
        // 根据RGBA 生成颜色对象
		color = [UIColor colorWithRed:(red/255.0f) green:(green/255.0f) blue:(blue/255.0f) alpha:(alpha/255.0f)];
	}

	// 操作完成后,释放上下文对象
	CGContextRelease(contexRef);
	// 从内存中释放掉 加载到内存的图像数据
	if (dataPoint) { free(dataPoint); }
    // 返回图片上该点对应的颜色
	return color;
}

// 自定义方法2:通过_imgView里面的image的引用,创建并返回对应的上下文,即根据CGImageRef来创建一个ARGBBitmapContext
- (CGContextRef)ARGBBitmapContextFromImage:(CGImageRef) inImage
{
    // 要创建的上下文
	CGContextRef    context = NULL;
    // 色彩空间
	CGColorSpaceRef colorSpace;
    // 位图数据在内存空间的首地址
	void *          bitmapData;
    // 每一行的字节数
	int             bitmapBytesPerRow;
    // 图片总的占的字节数
    int             bitmapByteCount;

	// 得到图片的宽度和高度,将要使用整个图片,创建上下文
	size_t pixelsWide = CGImageGetWidth(inImage);
	size_t pixelsHigh = CGImageGetHeight(inImage);

	// 每一行占多少字节. 本取色图片中的每一个像素点占4个字节;
    // 红 绿 蓝 透明度 各占一个字节(8位  取值范围0~255)
    // 每一行的字节数,因为每一个像素点占4个字节(包含RGBA)(其中一个R就是一个字节,占8位,取值是2的8次方 0~255)
	bitmapBytesPerRow   = (pixelsWide * 4);
    // 图片总的占的字节数
	bitmapByteCount     = (bitmapBytesPerRow * pixelsHigh);

	// 使用指定的 色彩空间(RGB)
	colorSpace = CGColorSpaceCreateDeviceRGB();
	if (colorSpace == NULL)
	{
		fprintf(stderr, "创建并分配色彩空间 出错\n");
		return NULL;
	}

	// 为取色图片数据  分配所有的内存空间
    // 所有画到取色图片上下文的操作,都将被渲染到此内存空间
	bitmapData = malloc( bitmapByteCount );
	if (bitmapData == NULL)
	{
		fprintf (stderr, "内存空间分配失败~");
		CGColorSpaceRelease( colorSpace );
		return NULL;
	}

	// 创建位图上下文. 使用 pre-multiplied ARGB, ARGB中的每一个成员都占8个bit位,即一字节,一个像素共占4个字节
    // 无论原取色图片的格式是什么(CMYK或Grayscale),都将通过CGBitmapContextCreate方法,转成指定的ARGB格式
	context = CGBitmapContextCreate (bitmapData,
									 pixelsWide,
									 pixelsHigh,
									 8,      // bits per component
									 bitmapBytesPerRow,
									 colorSpace,
									 (CGBitmapInfo)kCGImageAlphaPremultipliedFirst);
	if (context == NULL)
	{
		free (bitmapData);
		fprintf (stderr, "位图上下文创建失败~");
	}

	// 在返回上下文之前 必须记得释放 色彩空间
	CGColorSpaceRelease( colorSpace );

	return context;
}

@end

ColorPicker控制器及其代理

//
//  ColorPickerController.h
//  26_popOverCtrl
//
//  Created by beyond on 14-8-31.
//  Copyright (c) 2014年 com.beyond. All rights reserved.
//

#import <UIKit/UIKit.h>
@protocol ColorPickerDelegate;
@interface ColorPickerController : UIViewController

// 成员:代理,到时个通知该代理,选择的颜色是啥~
@property (weak, nonatomic) id<ColorPickerDelegate> delegate;
@end
//
//  ColorPickerController.m
//  26_popOverCtrl
//
//  Created by beyond on 14-8-31.
//  Copyright (c) 2014年 com.beyond. All rights reserved.
//

#import "ColorPickerController.h"
// 分类
#import "UIImage+Point2Color.h"
// 颜色选择完毕,通知代理
#import "ColorPickerDelegate.h"
@interface ColorPickerController ()

@property (weak, nonatomic) IBOutlet UIImageView *imageView;
@end

@implementation ColorPickerController

#pragma mark - 生命周期方法
- (void)viewDidLoad
{
    [super viewDidLoad];

    // 重要~~~指定 当前控制器在popover中显示的大小(跟 图片 一样)
    self.preferredContentSize = self.imageView.image.size;
}
// 触摸结束时,获取点击的坐标,调用UIImage分类方法,获取图片上该点的颜色
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event
{
    // 有人需要该点的颜色,才进行取色
    if ([self.delegate respondsToSelector:@selector(colorPickerController:didSelectedColor:)]) {
        // 获得触摸点
        UITouch *touch = [touches anyObject];
        CGPoint point = [touch locationInView:touch.view];

        // 获得颜色
        UIColor *color = [self.imageView.image colorFromPoint:point];
        // 告诉代理,该点对应的颜色
        [self.delegate colorPickerController:self didSelectedColor:color];
    }
}

@end
//
//  ColorPickerDelegate.h
//  26_popOverCtrl
//
//  Created by beyond on 14-8-31.
//  Copyright (c) 2014年 com.beyond. All rights reserved.
//  颜色选择控制器的代理,当它解码出用户点击处的颜色时,通知代理

#import <Foundation/Foundation.h>
@class ColorPickerController;
@protocol ColorPickerDelegate <NSObject>

@optional
- (void)colorPickerController:(ColorPickerController *)ctrl didSelectedColor:(UIColor *)color;

@end

主控制器

//
//  BeyondViewController.m
//  26_popOverCtrl
//
//  Created by beyond on 14-8-31.
//  Copyright (c) 2014年 com.beyond. All rights reserved.
// 00000000
// 99999999

#import "BeyondViewController.h"

// 点击左边Item,弹出Nana控制器
#import "NanaViewController.h"
// 点击中间的按钮,弹出颜色选择控制器
#import "ColorPickerController.h"
// 代理方法
#import "ColorPickerDelegate.h"

@interface BeyondViewController ()<ColorPickerDelegate>

- (IBAction)menuClick:(UIBarButtonItem *)sender;

- (IBAction)colorButtonClick:(UIButton *)sender;

// UIPopoverController  不能是局部变量,必须是成员变量
@property (nonatomic, strong) UIPopoverController *menuPopover;
// UIPopoverController  不能是局部变量,必须是成员变量
@property (nonatomic, strong) UIPopoverController *colorPopover;

@end

@implementation BeyondViewController

#pragma mark - 懒加载 getter方法
- (UIPopoverController *)menuPopover
{
    if (_menuPopover == nil) {
        // 1.创建内容控制器
        NanaViewController *nana = [[NanaViewController alloc] init];
        UINavigationController *nav = [[UINavigationController alloc] initWithRootViewController:nana];

        // 2.创建popover
        self.menuPopover = [[UIPopoverController alloc] initWithContentViewController:nav];
    }
    // 返回popOver
    return _menuPopover;
}

- (UIPopoverController *)colorPopover
{
    if (_colorPopover == nil) {
        // 1.创建内容控制器
        ColorPickerController *cpvc = [[ColorPickerController alloc] init];
        cpvc.delegate = self;

        // 2.创建popover
        self.colorPopover = [[UIPopoverController alloc] initWithContentViewController:cpvc];
        // 重要~~~点击popOver之外的阴影,使点击事件可以穿透...
        // self.colorPopover.passthroughViews = @[self.colorButton];
    }
    return _colorPopover;
}

#pragma mark - 颜色选择控制器的代理方法
- (void)colorPickerController:(ColorPickerController *)cpvc didSelectedColor:(UIColor *)color
{
    self.view.backgroundColor = color;
}

#pragma mark - 监听按钮点击
/**
 *  点击菜单,在指定位置,弹出popOver
 */
- (IBAction)menuClick:(UIBarButtonItem *)sender
{
    // 显示到哪个位置
    [self.menuPopover presentPopoverFromBarButtonItem:sender permittedArrowDirections:UIPopoverArrowDirectionAny animated:YES];
}

/**
 *  点击了颜色按钮,在指定位置,弹出popOver
 */
- (IBAction)colorButtonClick:(UIButton *)sender
{
    [self.colorPopover presentPopoverFromRect:sender.bounds inView:sender permittedArrowDirections:UIPopoverArrowDirectionAny animated:YES];
}
@end
时间: 2024-10-07 04:17:30

iOS_26PopoverController简单使用的相关文章

C# Ping 简单使用

编程过程中,有时候需要判断主机是否在线,最简单的方法就是使用Windows的Ping命令看看能否ping通.看到网上很多文章,说用C#去调用windows的ping.exe,然后解析返回的字符串.我觉得这种方式太麻烦了,就做一下简单判断,不想弄那么麻烦. 查了一下,C#专门提供了一个Ping类,与Windows下的ping命令类似: 命令空间: System.Net.NetworkInformation; 使用方法: bool online = false; //是否在线 Ping ping =

自动生成简单四则运算的C语言程序

该程序是在博客园里面找的,具体是谁的找了半天没找到,无法提供它原本的链接.由于自己写的过于简单,且有一些功能暂时无法实现,所以就找了一个来应付作业,望原谅.在这个程序的源码中我改了一个错误的地方,源码中有这样一个随机数发生器的初始化函数的语句:"srand((unsigned)time(NULL))".srand函数是随机数发生器的初始化函数.但是正确的写法应该是:srand(unsigned( time(NULL))):为了防止随机数每次重复,常常使用系统时间来初始化,即使用time

Mysql的锁机制与PHP文件锁处理高并发简单思路

以购买商品举例: ① 从数据库获取库存的数量. ② 检查一下库存的数量是否充足. ③ 库存的数量减去买家购买的数量(以每个用户购买一个为例). ④ 最后完成购买. 仅仅这几行逻辑代码在并发的情况下会出现问题,自己可以想象一下. 这里暂时就不测试了,下面会针对并发的处理给出测试结果. 创建表: CREATE TABLE `warehouse` ( `id` int(11) NOT NULL AUTO_INCREMENT COMMENT 'id', `stock` int(11) NOT NULL

Winfrom 简单的安卓手机屏幕获取和安卓简单操作

为啥我要做这个东西了,是因为经常要用投影演示app ,现在有很多这样的软件可以把手机界面投到电脑上 ,但都要安装,比如说360的手机助手,我又讨厌安装,于是就自己捣鼓了下 做了这个东西, 实现了以下简单功能   1.屏幕获取(因为是截图方式获取的,所以有点卡顿) 2.实现点击功能,并在点击的时候出现一个手势图标,方便用户观看 3.实现简单的滑动功能 4.实现在界面上画图功能 5.实现拖拽安装apk功能 操作说明:鼠标左边 模拟手机点击,中键停止/开始刷新界面(画图的时候不能刷新),右键去掉画图内

iOS instruments之ui automation的简单使用(高手绕道)

最近使用了几次instruments中的automation工具,现记录下automation的简单使用方法,希望对没接触过自动化测试又有需求的人有所帮助.  UI 自动测试是iOS 中重要的附加功能,它由名为"Automation"的新的工具对象支持.Automation工具的脚本是用JavaScript语言编写,主要用于分析应用的性能和用户行为,模仿/击发被请求的事件,利用它可以完成对被测应用的简单的UI测试及相关功能测试. 一. 简单的录制脚本 打开xcode,这里用我为我家亲爱

Android ExpandableListView 带有Checkbox的简单应用

expandablelistview2_groups.xml <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height=&qu

Android ExpandableListView的简单应用

Expandablelistview1Activity.java package com.wangzhu.demoexpandablelistview; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import android.app.Activity; import android.os.Bundle; import android.widg

一个简单的主机管理模拟程序

最近写的一个小练习,主要是把前面学的东西整合一下.写了一个简单的主机管理界面,主要是练习以下知识点: Session和Cookie进行登录验证(装饰器) 数据库的基本操作 (单表,1对多,多对多) Form的简单使用实现验证 Bootstrap模板写个简单界面 自定义分页 信号,中间件,CSRF,模板语言,JavaScript,AJAX等等 界面比较low,毕竟不是专业的. 附件里面是Django的源代码,3个文件放在一起winrar解压就可以打开

简单介绍一下vue2.0

Vue Vue是用于构建用户界面的渐进框架.作者尤雨熙特别强调它与其他的框架不同,Vue是渐进式的框架,可以逐步采用,不必一下就通过框架去重构项目. 另外Vue的核心库只专注于视图层,这样就更容易与其他库或现有项目进行集成,也更灵活. Vue在兼容性上不支持IE8以下版本的浏览器,用到了ECMAScript 5的功能,所有支持ECMAScript 5的浏览器都没问题,像这些: 安装 如果你已经熟悉并安装webpack那可以直接装一个CLI版即命令行工具,快速方便. $ npm install -