注: このアプリは内部使用のみを目的として作成しています。
Apple には CoreTelephony と呼ばれるフレームワークがあり、通話の受信、切断などでコールバックを提供します。私がしようとしているのは、通話を切断するか、他の番号に転送することです。
私はこれに多くの時間を費やしましたが、通話を切断する方法がわかりません。どんな助けでも大歓迎です。
注: このアプリは内部使用のみを目的として作成しています。
Apple には CoreTelephony と呼ばれるフレームワークがあり、通話の受信、切断などでコールバックを提供します。私がしようとしているのは、通話を切断するか、他の番号に転送することです。
私はこれに多くの時間を費やしましたが、通話を切断する方法がわかりません。どんな助けでも大歓迎です。
これは github で見つけた私のコードではありません。自分でテストし、必要に応じて変更しましたが、引き続き使用できます。余分なコードを削除するだけです。
//
// CallHandler.h
// PhoneCallBlock
//
// Created by Hui Li on 12-5-11.
// Copyright (c) 2012年 hust. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "MobileControlHandler.h"
@interface CallHandler : NSObject
{
//
}
static void callback(CFNotificationCenterRef center, void *observer, CFStringRef name, const void *object, CFDictionaryRef userInfo);
static void signalHandler(int sigraised);
+ (void)start;
+ (void)stop;
@end
//
// CallHandler.m
// PhoneCallBlock
//
// Created by Hui Li on 12-5-11.
// Copyright (c) 2012年 hust. All rights reserved.
//
#import "CallHandler.h"
static BOOL isGlobalCallBlock;
@implementation CallHandler
extern NSString* const kCTSMSMessageReceivedNotification;
extern NSString* const kCTSMSMessageReplaceReceivedNotification;
extern NSString* const kCTSIMSupportSIMStatusNotInserted;
extern NSString* const kCTSIMSupportSIMStatusReady;
typedef struct __CTCall CTCall;
extern NSString *CTCallCopyAddress(void*, CTCall *);
extern void CTCallDisconnect(CTCall*);
void* CTSMSMessageSend(id server,id msg);
typedef struct __CTSMSMessage CTSMSMessage;
NSString *CTSMSMessageCopyAddress(void *, CTSMSMessage *);
NSString *CTSMSMessageCopyText(void *, CTSMSMessage *);
int CTSMSMessageGetRecordIdentifier(void * msg);
NSString * CTSIMSupportGetSIMStatus();
NSString * CTSIMSupportCopyMobileSubscriberIdentity();
id CTSMSMessageCreate(void* unknow/*always 0*/,NSString* number,NSString* text);
void * CTSMSMessageCreateReply(void* unknow/*always 0*/,void * forwardTo,NSString* text);
id CTTelephonyCenterGetDefault(void);
void CTTelephonyCenterAddObserver(id,id,CFNotificationCallback,NSString*,void*,int);
void CTTelephonyCenterRemoveObserver(id,id,NSString*,void*);
int CTSMSMessageGetUnreadCount(void);
#pragma mark - Call Block Methods
+ (void)start
{
@autoreleasepool
{
// Initialize listener by adding CT Center observer implicit
id ct = CTTelephonyCenterGetDefault();
CTTelephonyCenterAddObserver( ct, NULL, callback,NULL,NULL,
CFNotificationSuspensionBehaviorHold);
// Handle Interrupts
sig_t oldHandler = signal(SIGINT, signalHandler);
if (oldHandler == SIG_ERR)
{
printf("Could not establish new signal handler");
exit(1);
}
// Run loop lets me catch notifications
printf("Starting run loop and watching for notification.\n");
CFRunLoopRun();
// Shouldn't ever get here. Bzzzt
printf("Unexpectedly back from CFRunLoopRun()!\n");
[CallHandler stop];
[[MobileControlHandler sharedInstance] selfScheduledTimer];
}
}
BOOL runLoopIsStopped;
+ (void)stop
{
@autoreleasepool
{
CFRunLoopStop(CFRunLoopGetCurrent());
//
// NSRunLoop *runLoop = [NSRunLoop currentRunLoop];
// NSDate *date = [NSDate distantFuture];
// while (!runLoopIsStopped && [runLoop runMode:NSDefaultRunLoopMode beforeDate:date]);
printf("Stopping run loop and removing watch for notification.\n");
}
}
- (void)startCFRunLoopRun
{
CFRunLoopRun();
}
static void callback(CFNotificationCenterRef center, void *observer, CFStringRef name, const void *object, CFDictionaryRef userInfo)
{
NSString *notifyname=(NSString *)name;
if ([notifyname isEqualToString:@"kCTCallStatusChangeNotification"])//电话
{
NSDictionary *info = (NSDictionary*)userInfo;
NSString *state=[info[@"kCTCallStatus"] stringValue];
if ([state isEqualToString:@"5"])//disconnect
NSLog(@"Missed phone call: %@",state);
}
else if ([notifyname isEqualToString:@"kCTCallIdentificationChangeNotification"])
{
NSDictionary *info = (NSDictionary *)userInfo;
CTCall *call = (CTCall *)info[@"kCTCall"];
NSString *caller = CTCallCopyAddress(NULL, call);
NSLog(@"Phone Number: %@",caller);
// #0
NSString *defaultsKey = [[NSUserDefaults standardUserDefaults] objectForKey:[[MobileControlHandler sharedInstance] getCallBlockDefaultsKey]];
if ([defaultsKey isEqualToString:@"YES"])
{
//disconnect this call
NSLog(@"Disconnect all phone calls");
CTCallDisconnect(call);
}
// #1
/*
NSMutableArray *arrayOfAllPhones = [[MobileControlHandler sharedInstance] getAllContactsPhoneNumbers];
for (int i = 0; i < arrayOfAllPhones.count; i++)
{
NSString *phoneNumber = [arrayOfAllPhones objectAtIndex:i];
if ([caller isEqualToString:phoneNumber])
{
//disconnect this call
NSLog(@"挂雷冰");
CTCallDisconnect(call);
}
}
*/
// #2
/*
if ([caller isEqualToString:@"1800-800-800"])
{
//disconnect this call
NSLog(@"挂雷冰");
CTCallDisconnect(call);
}
*/
}
else if ([notifyname isEqualToString:@"kCTMessageReceivedNotification"])//收到短信
{
/*
kCTMessageIdKey = "-2147483636";
kCTMessageTypeKey = 1;
*/
NSDictionary *info = (NSDictionary *)userInfo;
CFNumberRef msgID = (CFNumberRef)info[@"kCTMessageIdKey"];
int result;
CFNumberGetValue((CFNumberRef)msgID, kCFNumberSInt32Type, &result);
Class CTMessageCenter = NSClassFromString(@"CTMessageCenter");
id mc = [CTMessageCenter sharedMessageCenter];
id incMsg = [mc incomingMessageWithId: result];
int msgType = (int)[incMsg messageType];
if (msgType == 1) //experimentally detected number
{
id phonenumber = [incMsg sender];
NSString *senderNumber = (NSString *)[phonenumber canonicalFormat];
id incMsgPart = [incMsg items][0];
NSData *smsData = [incMsgPart data];
NSString *smsText = [[NSString alloc] initWithData:smsData encoding:NSUTF8StringEncoding];
}
}
else if ([notifyname isEqualToString:@"kCTIndicatorsSignalStrengthNotification"])//信号
{
/*
kCTIndicatorsGradedSignalStrength = 2;
kCTIndicatorsRawSignalStrength = "-101";
kCTIndicatorsSignalStrength = 19;
*/
}
else if ([notifyname isEqualToString:@"kCTRegistrationStatusChangedNotification"])//网络注册状态
{
/*
kCTRegistrationInHomeCountry = 1;
kCTRegistrationStatus = kCTRegistrationStatusRegisteredHome;
*/
}
else if ([notifyname isEqualToString:@"kCTRegistrationDataStatusChangedNotification"])
{
/*
kCTRegistrationDataActive = 1;
kCTRegistrationDataAttached = 1;
kCTRegistrationDataConnectionServices = (
kCTDataConnectionServiceTypeInternet,
kCTDataConnectionServiceTypeWirelessModemTraffic,
kCTDataConnectionServiceTypeWirelessModemAuthentication
);
kCTRegistrationDataContextID = 0;
kCTRegistrationDataIndicator = kCTRegistrationDataIndicator3G;
kCTRegistrationDataStatus = kCTRegistrationDataStatusAttachedAndActive;
kCTRegistrationDataStatusInternationalRoaming = 1;
kCTRegistrationRadioAccessTechnology = kCTRegistrationRadioAccessTechnologyUTRAN;
*/
}
else if ([notifyname isEqualToString:@"kCTRegistrationCellChangedNotification"])
{
/*
kCTRegistrationGsmCellId = 93204174;
kCTRegistrationGsmLac = 55583;
kCTRegistrationInHomeCountry = 1;
kCTRegistrationRadioAccessTechnology = kCTRegistrationRadioAccessTechnologyUTRAN;
*/
}
else if ([notifyname isEqualToString:@"kCTIndicatorRadioTransmitNotification"])
{
/*
kCTRadioTransmitDCHStatus = 1;
*/
}
//NSLog(@"First Name: %@, Details :%@", notifyname,cuserInfo);
}
static void signalHandler(int sigraised)
{
NSLog(@"\nInterrupted.\n");
exit(0);
}
@end