Voice mail feature: display number of unread messages on status bar and reformat code

This commit is contained in:
Gautier Pelloux-Prayer 2014-09-24 16:34:48 +02:00
parent 9c9a7fe26d
commit 55a88095bd
8 changed files with 1340 additions and 1236 deletions

View file

@ -4,18 +4,18 @@
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
*/
#import <Foundation/Foundation.h>
#import <AVFoundation/AVAudioSession.h>
@ -50,6 +50,7 @@ extern NSString *const kLinphoneSettingsUpdate;
extern NSString *const kLinphoneBluetoothAvailabilityUpdate;
extern NSString *const kLinphoneConfiguringStateUpdate;
extern NSString *const kLinphoneGlobalStateUpdate;
extern NSString *const kLinphoneNotifyReceived;
typedef enum _NetworkType {
network_none = 0,
@ -105,7 +106,7 @@ typedef struct _LinphoneManagerSounds {
@interface LinphoneManager : NSObject {
@protected
SCNetworkReachabilityRef proxyReachability;
@private
NSTimer* mIterateTimer;
NSMutableArray* pendindCallIdFromRemoteNotif;
@ -174,7 +175,7 @@ typedef struct _LinphoneManagerSounds {
- (NSInteger)lpConfigIntForKey:(NSString*)key;
- (void)lpConfigSetInt:(NSInteger)value forKey:(NSString*)key forSection:(NSString*)section;
- (NSInteger)lpConfigIntForKey:(NSString*)key forSection:(NSString*)section;
- (void)lpConfigSetBool:(BOOL)value forKey:(NSString*)key;
- (void)lpConfigSetBool:(BOOL)value forKey:(NSString*)key;
- (BOOL)lpConfigBoolForKey:(NSString*)key;
- (void)lpConfigSetBool:(BOOL)value forKey:(NSString*)key forSection:(NSString*)section;
- (BOOL)lpConfigBoolForKey:(NSString*)key forSection:(NSString*)section;

File diff suppressed because it is too large Load diff

View file

@ -1,8 +1,8 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="5056" systemVersion="13C1021" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none">
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="6245" systemVersion="13F34" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none">
<dependencies>
<deployment defaultVersion="1536" identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="3733"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="6238"/>
</dependencies>
<objects>
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner" customClass="UICallBar">
@ -59,7 +59,7 @@
<rect key="frame" x="0.0" y="0.0" width="281" height="260"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
</imageView>
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="3" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="73" userLabel="1" customClass="UIDigitButton">
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="3" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="73" userLabel="1" customClass="UIDigitButtonLongVoiceMail">
<rect key="frame" x="-20" y="10" width="107" height="54"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<color key="backgroundColor" red="0.40000001000000002" green="1" blue="1" alpha="0.0" colorSpace="calibratedRGB"/>
@ -160,7 +160,7 @@
</state>
<state key="highlighted" image="numpad_star_over.png"/>
</button>
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="13" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="64" userLabel="0" customClass="UIDigitButton">
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="13" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="64" userLabel="0" customClass="UIDigitButtonLongPlus">
<rect key="frame" x="87" y="196" width="106" height="54"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<accessibility key="accessibilityConfiguration" label="0"/>
@ -481,6 +481,8 @@
</view>
</subviews>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="calibratedWhite"/>
<nil key="simulatedStatusBarMetrics"/>
<freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
</view>
<view contentMode="scaleToFill" id="100" userLabel="Landscape View" customClass="UITransparentView">
<rect key="frame" x="0.0" y="0.0" width="480" height="320"/>
@ -499,7 +501,7 @@
<rect key="frame" x="0.0" y="0.0" width="281" height="260"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
</imageView>
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="3" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="115" userLabel="1" customClass="UIDigitButton">
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="3" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="115" userLabel="1" customClass="UIDigitButtonLongVoiceMail">
<rect key="frame" x="-20" y="10" width="107" height="54"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<color key="backgroundColor" red="0.40000001000000002" green="1" blue="1" alpha="0.0" colorSpace="calibratedRGB"/>
@ -590,7 +592,7 @@
</state>
<state key="highlighted" image="numpad_star_over.png"/>
</button>
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="13" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="125" userLabel="0" customClass="UIDigitButton">
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="13" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="125" userLabel="0" customClass="UIDigitButtonLongPlus">
<rect key="frame" x="87" y="196" width="106" height="54"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<fontDescription key="fontDescription" name="Helvetica-Bold" family="Helvetica" pointSize="15"/>
@ -897,7 +899,9 @@
</view>
</subviews>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="calibratedWhite"/>
<nil key="simulatedStatusBarMetrics"/>
<simulatedOrientationMetrics key="simulatedOrientationMetrics" orientation="landscapeRight"/>
<freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
</view>
</objects>
<resources>
@ -1026,4 +1030,9 @@
<image name="video_on_default.png" width="160" height="134"/>
<image name="video_on_default_landscape.png" width="130" height="163"/>
</resources>
<simulatedMetricsContainer key="defaultSimulatedMetrics">
<simulatedStatusBarMetrics key="statusBar"/>
<simulatedOrientationMetrics key="orientation"/>
<simulatedScreenMetrics key="destination" type="retina4"/>
</simulatedMetricsContainer>
</document>

View file

@ -1,8 +1,8 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.iPad.XIB" version="3.0" toolsVersion="5056" systemVersion="13C1021" targetRuntime="iOS.CocoaTouch.iPad" propertyAccessControl="none">
<document type="com.apple.InterfaceBuilder3.CocoaTouch.iPad.XIB" version="3.0" toolsVersion="6245" systemVersion="13F34" targetRuntime="iOS.CocoaTouch.iPad" propertyAccessControl="none">
<dependencies>
<deployment defaultVersion="1536" identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="3733"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="6238"/>
</dependencies>
<objects>
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner" customClass="UICallBar">
@ -54,7 +54,7 @@
<rect key="frame" x="0.0" y="0.0" width="281" height="260"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
</imageView>
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="3" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="58" userLabel="1" customClass="UIDigitButton">
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="3" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="58" userLabel="1" customClass="UIDigitButtonLongVoiceMail">
<rect key="frame" x="-20" y="10" width="107" height="54"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<color key="backgroundColor" red="0.40000001000000002" green="1" blue="1" alpha="0.0" colorSpace="calibratedRGB"/>
@ -145,7 +145,7 @@
</state>
<state key="highlighted" image="numpad_star_over.png"/>
</button>
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="13" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="48" userLabel="0" customClass="UIDigitButton">
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="13" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="48" userLabel="0" customClass="UIDigitButtonLongPlus">
<rect key="frame" x="87" y="196" width="106" height="54"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<fontDescription key="fontDescription" name="Helvetica-Bold" family="Helvetica" pointSize="15"/>
@ -352,7 +352,9 @@
</view>
</subviews>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="calibratedWhite"/>
<nil key="simulatedStatusBarMetrics"/>
<simulatedOrientationMetrics key="simulatedOrientationMetrics" orientation="landscapeRight"/>
<freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
</view>
<view autoresizesSubviews="NO" contentMode="scaleToFill" id="3" userLabel="Portrait View" customClass="UITransparentView">
<rect key="frame" x="0.0" y="0.0" width="768" height="1004"/>
@ -371,7 +373,7 @@
<rect key="frame" x="0.0" y="0.0" width="281" height="260"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
</imageView>
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="3" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="19" userLabel="1" customClass="UIDigitButton">
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="3" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="19" userLabel="1" customClass="UIDigitButtonLongVoiceMail">
<rect key="frame" x="-20" y="10" width="107" height="54"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<color key="backgroundColor" red="0.40000001000000002" green="1" blue="1" alpha="0.0" colorSpace="calibratedRGB"/>
@ -472,7 +474,7 @@
</state>
<state key="highlighted" image="numpad_star_over.png"/>
</button>
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="13" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="29" userLabel="0" customClass="UIDigitButton">
<button opaque="NO" clearsContextBeforeDrawing="NO" tag="13" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" id="29" userLabel="0" customClass="UIDigitButtonLongPlus">
<rect key="frame" x="87" y="196" width="106" height="54"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<accessibility key="accessibilityConfiguration" label="0"/>
@ -696,6 +698,8 @@
</view>
</subviews>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="calibratedWhite"/>
<nil key="simulatedStatusBarMetrics"/>
<freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
</view>
</objects>
<resources>
@ -787,4 +791,9 @@
<image name="video_on_default.png" width="162" height="170"/>
<image name="video_on_default_landscape.png" width="162" height="170"/>
</resources>
<simulatedMetricsContainer key="defaultSimulatedMetrics">
<simulatedStatusBarMetrics key="statusBar"/>
<simulatedOrientationMetrics key="orientation"/>
<simulatedScreenMetrics key="destination"/>
</simulatedMetricsContainer>
</document>

View file

@ -36,6 +36,7 @@
LinphoneManager* lm = [LinphoneManager instance];
NSString * voiceMailUri = [lm lpConfigStringForKey:@"voice_mail_uri" withDefault:NULL];
if (voiceMailUri != NULL) {
[lm call:voiceMailUri displayName:NSLocalizedString(@"Voice mail",nil) transfer:FALSE];
}

View file

@ -4,18 +4,18 @@
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Library General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Library General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
*/
#import <UIKit/UIKit.h>
#import "TPMultiLayoutViewController.h"
@ -30,7 +30,9 @@
@property (nonatomic, retain) IBOutlet UIImageView* callQualityImage;
@property (nonatomic, retain) IBOutlet UIImageView* callSecurityImage;
@property (nonatomic, retain) IBOutlet UIButton* callSecurityButton;
@property (retain, nonatomic) IBOutlet UILabel *voicemailCount;
- (IBAction)doSecurityClick:(id)sender;
@end

View file

@ -4,18 +4,18 @@
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Library General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Library General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
*/
#import "UIStateBar.h"
#import "LinphoneManager.h"
@ -36,290 +36,330 @@ NSTimer *callSecurityTimer;
#pragma mark - Lifecycle Functions
- (id)init {
self = [super initWithNibName:@"UIStateBar" bundle:[NSBundle mainBundle]];
if(self != nil) {
self->callSecurityImage = nil;
self->callQualityImage = nil;
self->securitySheet = nil;
}
return self;
self = [super initWithNibName:@"UIStateBar" bundle:[NSBundle mainBundle]];
if(self != nil) {
self->callSecurityImage = nil;
self->callQualityImage = nil;
self->securitySheet = nil;
}
return self;
}
- (void) dealloc {
if(securitySheet) {
[securitySheet release];
}
[registrationStateImage release];
[registrationStateLabel release];
[callQualityImage release];
[callSecurityImage release];
[callSecurityButton release];
[[NSNotificationCenter defaultCenter] removeObserver:self];
[callQualityTimer invalidate];
[callQualityTimer release];
[super dealloc];
if(securitySheet) {
[securitySheet release];
}
[registrationStateImage release];
[registrationStateLabel release];
[callQualityImage release];
[callSecurityImage release];
[callSecurityButton release];
[[NSNotificationCenter defaultCenter] removeObserver:self];
[callQualityTimer invalidate];
[callQualityTimer release];
[_voicemailCount release];
[super dealloc];
}
#pragma mark - ViewController Functions
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
// Set callQualityTimer
callQualityTimer = [NSTimer scheduledTimerWithTimeInterval:1
target:self
selector:@selector(callQualityUpdate)
userInfo:nil
repeats:YES];
// Set callQualityTimer
callSecurityTimer = [NSTimer scheduledTimerWithTimeInterval:1
target:self
selector:@selector(callSecurityUpdate)
userInfo:nil
repeats:YES];
// Set observer
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(registrationUpdate:)
name:kLinphoneRegistrationUpdate
object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(globalStateUpdate:)
name:kLinphoneGlobalStateUpdate
object:nil];
[callQualityImage setHidden: true];
[callSecurityImage setHidden: true];
// Update to default state
LinphoneProxyConfig* config = NULL;
if([LinphoneManager isLcReady])
linphone_core_get_default_proxy([LinphoneManager getLc], &config);
[self proxyConfigUpdate: config];
[super viewWillAppear:animated];
// Set callQualityTimer
callQualityTimer = [NSTimer scheduledTimerWithTimeInterval:1
target:self
selector:@selector(callQualityUpdate)
userInfo:nil
repeats:YES];
// Set callQualityTimer
callSecurityTimer = [NSTimer scheduledTimerWithTimeInterval:1
target:self
selector:@selector(callSecurityUpdate)
userInfo:nil
repeats:YES];
// Set observer
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(registrationUpdate:)
name:kLinphoneRegistrationUpdate
object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(globalStateUpdate:)
name:kLinphoneGlobalStateUpdate
object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(notifyReceived:)
name:kLinphoneNotifyReceived
object:nil];
[callQualityImage setHidden: true];
[callSecurityImage setHidden: true];
self.voicemailCount.hidden = true;
// Update to default state
LinphoneProxyConfig* config = NULL;
if([LinphoneManager isLcReady])
linphone_core_get_default_proxy([LinphoneManager getLc], &config);
[self proxyConfigUpdate: config];
}
- (void)viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
// Remove observer
[[NSNotificationCenter defaultCenter] removeObserver:self
name:kLinphoneRegistrationUpdate
object:nil];
[[NSNotificationCenter defaultCenter] removeObserver:self
name:kLinphoneGlobalStateUpdate
object:nil];
if(callQualityTimer != nil) {
[callQualityTimer invalidate];
callQualityTimer = nil;
}
if(callSecurityTimer != nil) {
[callSecurityTimer invalidate];
callSecurityTimer = nil;
}
[super viewWillDisappear:animated];
// Remove observer
[[NSNotificationCenter defaultCenter] removeObserver:self
name:kLinphoneRegistrationUpdate
object:nil];
[[NSNotificationCenter defaultCenter] removeObserver:self
name:kLinphoneGlobalStateUpdate
object:nil];
[[NSNotificationCenter defaultCenter] removeObserver:self
name:kLinphoneNotifyReceived
object:nil];
if(callQualityTimer != nil) {
[callQualityTimer invalidate];
callQualityTimer = nil;
}
if(callSecurityTimer != nil) {
[callSecurityTimer invalidate];
callSecurityTimer = nil;
}
}
#pragma mark - Event Functions
- (void)registrationUpdate: (NSNotification*) notif {
LinphoneProxyConfig* config = NULL;
linphone_core_get_default_proxy([LinphoneManager getLc], &config);
[self proxyConfigUpdate:config];
- (void)registrationUpdate: (NSNotification*) notif {
LinphoneProxyConfig* config = NULL;
linphone_core_get_default_proxy([LinphoneManager getLc], &config);
[self proxyConfigUpdate:config];
}
- (void) globalStateUpdate:(NSNotification*) notif {
if ([LinphoneManager isLcReady]) [self registrationUpdate:notif];
if ([LinphoneManager isLcReady]) [self registrationUpdate:notif];
}
- (void) notifyReceived:(NSNotification*) notif {
const LinphoneContent * content = [[notif.userInfo objectForKey: @"content"] pointerValue];
#pragma mark -
if ((content == NULL)
|| (strcmp("application", content->type) != 0)
|| (strcmp("simple-message-summary", content->subtype) != 0)
|| (content->data == NULL)) {
return;
}
const char * body = (const char*) content->data;
if ((body = strstr(body, "voice-message: ")) == NULL) {
[LinphoneLogger log:LinphoneLoggerWarning format:@"Received new NOTIFY from voice mail but could not find 'voice-message' in BODY. Ignoring it."];
return;
}
int unreadCount = 0;
sscanf(body, "voice-message: %d", &unreadCount);
[LinphoneLogger log:LinphoneLoggerLog format:@"Received new NOTIFY from voice mail: there is/are now %d message(s) unread", unreadCount];
if (unreadCount > 0) {
self.voicemailCount.hidden = FALSE;
self.voicemailCount.text = [NSString stringWithFormat:NSLocalizedString(@"%d unread messages", @"%d"), unreadCount];
} else {
self.voicemailCount.hidden = TRUE;
}
}
#pragma mark -
- (void)proxyConfigUpdate: (LinphoneProxyConfig*) config {
LinphoneRegistrationState state = LinphoneRegistrationNone;
NSString* message = nil;
UIImage* image = nil;
LinphoneCore* lc = [LinphoneManager getLc];
LinphoneGlobalState gstate = linphone_core_get_global_state(lc);
LinphoneRegistrationState state = LinphoneRegistrationNone;
NSString* message = nil;
UIImage* image = nil;
LinphoneCore* lc = [LinphoneManager getLc];
LinphoneGlobalState gstate = linphone_core_get_global_state(lc);
if( gstate == LinphoneGlobalConfiguring ){
message = NSLocalizedString(@"Fetching remote configuration", nil);
} else if (config == NULL) {
state = LinphoneRegistrationNone;
if(![LinphoneManager isLcReady] || linphone_core_is_network_reachable([LinphoneManager getLc]))
message = NSLocalizedString(@"No SIP account configured", nil);
else
message = NSLocalizedString(@"Network down", nil);
} else {
state = linphone_proxy_config_get_state(config);
switch (state) {
case LinphoneRegistrationOk:
message = NSLocalizedString(@"Registered", nil); break;
case LinphoneRegistrationNone:
case LinphoneRegistrationCleared:
message = NSLocalizedString(@"Not registered", nil); break;
case LinphoneRegistrationFailed:
message = NSLocalizedString(@"Registration failed", nil); break;
case LinphoneRegistrationProgress:
message = NSLocalizedString(@"Registration in progress", nil); break;
default: break;
}
}
if( gstate == LinphoneGlobalConfiguring ){
message = NSLocalizedString(@"Fetching remote configuration", nil);
} else if (config == NULL) {
state = LinphoneRegistrationNone;
if(![LinphoneManager isLcReady] || linphone_core_is_network_reachable([LinphoneManager getLc]))
message = NSLocalizedString(@"No SIP account configured", nil);
else
message = NSLocalizedString(@"Network down", nil);
} else {
state = linphone_proxy_config_get_state(config);
registrationStateLabel.hidden = NO;
switch(state) {
case LinphoneRegistrationFailed:
registrationStateImage.hidden = NO;
image = [UIImage imageNamed:@"led_error.png"];
break;
case LinphoneRegistrationCleared:
case LinphoneRegistrationNone:
registrationStateImage.hidden = NO;
image = [UIImage imageNamed:@"led_disconnected.png"];
break;
case LinphoneRegistrationProgress:
registrationStateImage.hidden = NO;
image = [UIImage imageNamed:@"led_inprogress.png"];
break;
case LinphoneRegistrationOk:
registrationStateImage.hidden = NO;
image = [UIImage imageNamed:@"led_connected.png"];
break;
}
[registrationStateLabel setText:message];
[registrationStateImage setImage:image];
switch (state) {
case LinphoneRegistrationOk:
message = NSLocalizedString(@"Registered", nil); break;
case LinphoneRegistrationNone:
case LinphoneRegistrationCleared:
message = NSLocalizedString(@"Not registered", nil); break;
case LinphoneRegistrationFailed:
message = NSLocalizedString(@"Registration failed", nil); break;
case LinphoneRegistrationProgress:
message = NSLocalizedString(@"Registration in progress", nil); break;
default: break;
}
}
registrationStateLabel.hidden = NO;
switch(state) {
case LinphoneRegistrationFailed:
registrationStateImage.hidden = NO;
image = [UIImage imageNamed:@"led_error.png"];
break;
case LinphoneRegistrationCleared:
case LinphoneRegistrationNone:
registrationStateImage.hidden = NO;
image = [UIImage imageNamed:@"led_disconnected.png"];
break;
case LinphoneRegistrationProgress:
registrationStateImage.hidden = NO;
image = [UIImage imageNamed:@"led_inprogress.png"];
break;
case LinphoneRegistrationOk:
registrationStateImage.hidden = NO;
image = [UIImage imageNamed:@"led_connected.png"];
break;
}
[registrationStateLabel setText:message];
[registrationStateImage setImage:image];
}
#pragma mark -
#pragma mark -
- (void)callSecurityUpdate {
BOOL pending = false;
BOOL security = true;
if(![LinphoneManager isLcReady]) {
[callSecurityImage setHidden:true];
return;
}
const MSList *list = linphone_core_get_calls([LinphoneManager getLc]);
if(list == NULL) {
if(securitySheet) {
[securitySheet dismissWithClickedButtonIndex:securitySheet.destructiveButtonIndex animated:TRUE];
}
[callSecurityImage setHidden:true];
return;
}
while(list != NULL) {
LinphoneCall *call = (LinphoneCall*) list->data;
LinphoneMediaEncryption enc = linphone_call_params_get_media_encryption(linphone_call_get_current_params(call));
if(enc == LinphoneMediaEncryptionNone)
security = false;
else if(enc == LinphoneMediaEncryptionZRTP) {
if(!linphone_call_get_authentication_token_verified(call)) {
pending = true;
}
}
list = list->next;
}
if(security) {
if(pending) {
[callSecurityImage setImage:[UIImage imageNamed:@"security_pending.png"]];
} else {
[callSecurityImage setImage:[UIImage imageNamed:@"security_ok.png"]];
}
} else {
[callSecurityImage setImage:[UIImage imageNamed:@"security_ko.png"]];
}
[callSecurityImage setHidden: false];
BOOL pending = false;
BOOL security = true;
if(![LinphoneManager isLcReady]) {
[callSecurityImage setHidden:true];
return;
}
const MSList *list = linphone_core_get_calls([LinphoneManager getLc]);
if(list == NULL) {
if(securitySheet) {
[securitySheet dismissWithClickedButtonIndex:securitySheet.destructiveButtonIndex animated:TRUE];
}
[callSecurityImage setHidden:true];
return;
}
while(list != NULL) {
LinphoneCall *call = (LinphoneCall*) list->data;
LinphoneMediaEncryption enc = linphone_call_params_get_media_encryption(linphone_call_get_current_params(call));
if(enc == LinphoneMediaEncryptionNone)
security = false;
else if(enc == LinphoneMediaEncryptionZRTP) {
if(!linphone_call_get_authentication_token_verified(call)) {
pending = true;
}
}
list = list->next;
}
if(security) {
if(pending) {
[callSecurityImage setImage:[UIImage imageNamed:@"security_pending.png"]];
} else {
[callSecurityImage setImage:[UIImage imageNamed:@"security_ok.png"]];
}
} else {
[callSecurityImage setImage:[UIImage imageNamed:@"security_ko.png"]];
}
[callSecurityImage setHidden: false];
}
- (void)callQualityUpdate {
UIImage *image = nil;
if([LinphoneManager isLcReady]) {
LinphoneCall *call = linphone_core_get_current_call([LinphoneManager getLc]);
if(call != NULL) {
//FIXME double check call state before computing, may cause core dump
- (void)callQualityUpdate {
UIImage *image = nil;
if([LinphoneManager isLcReady]) {
LinphoneCall *call = linphone_core_get_current_call([LinphoneManager getLc]);
if(call != NULL) {
//FIXME double check call state before computing, may cause core dump
float quality = linphone_call_get_average_quality(call);
if(quality < 1) {
image = [UIImage imageNamed:@"call_quality_indicator_0.png"];
} else if (quality < 2) {
image = [UIImage imageNamed:@"call_quality_indicator_1.png"];
} else if (quality < 3) {
image = [UIImage imageNamed:@"call_quality_indicator_2.png"];
} else {
image = [UIImage imageNamed:@"call_quality_indicator_3.png"];
}
}
}
if(image != nil) {
[callQualityImage setHidden:false];
[callQualityImage setImage:image];
} else {
[callQualityImage setHidden:true];
}
if(quality < 1) {
image = [UIImage imageNamed:@"call_quality_indicator_0.png"];
} else if (quality < 2) {
image = [UIImage imageNamed:@"call_quality_indicator_1.png"];
} else if (quality < 3) {
image = [UIImage imageNamed:@"call_quality_indicator_2.png"];
} else {
image = [UIImage imageNamed:@"call_quality_indicator_3.png"];
}
}
}
if(image != nil) {
[callQualityImage setHidden:false];
[callQualityImage setImage:image];
} else {
[callQualityImage setHidden:true];
}
}
#pragma mark - Action Functions
- (IBAction)doSecurityClick:(id)sender {
if([LinphoneManager isLcReady] && linphone_core_get_calls_nb([LinphoneManager getLc])) {
LinphoneCall *call = linphone_core_get_current_call([LinphoneManager getLc]);
if(call != NULL) {
LinphoneMediaEncryption enc = linphone_call_params_get_media_encryption(linphone_call_get_current_params(call));
if(enc == LinphoneMediaEncryptionZRTP) {
bool valid = linphone_call_get_authentication_token_verified(call);
NSString *message = nil;
if(valid) {
message = NSLocalizedString(@"Remove trust in the peer?",nil);
} else {
message = [NSString stringWithFormat:NSLocalizedString(@"Confirm the following SAS with the peer:\n%s",nil),
linphone_call_get_authentication_token(call)];
}
if( securitySheet == nil ){
securitySheet = [[DTActionSheet alloc] initWithTitle:message];
[securitySheet setDelegate:self];
[securitySheet addButtonWithTitle:NSLocalizedString(@"Ok",nil) block:^(){
linphone_call_set_authentication_token_verified(call, !valid);
[securitySheet release];
securitySheet = nil;
}];
if([LinphoneManager isLcReady] && linphone_core_get_calls_nb([LinphoneManager getLc])) {
LinphoneCall *call = linphone_core_get_current_call([LinphoneManager getLc]);
if(call != NULL) {
LinphoneMediaEncryption enc = linphone_call_params_get_media_encryption(linphone_call_get_current_params(call));
if(enc == LinphoneMediaEncryptionZRTP) {
bool valid = linphone_call_get_authentication_token_verified(call);
NSString *message = nil;
if(valid) {
message = NSLocalizedString(@"Remove trust in the peer?",nil);
} else {
message = [NSString stringWithFormat:NSLocalizedString(@"Confirm the following SAS with the peer:\n%s",nil),
linphone_call_get_authentication_token(call)];
}
if( securitySheet == nil ){
securitySheet = [[DTActionSheet alloc] initWithTitle:message];
[securitySheet setDelegate:self];
[securitySheet addButtonWithTitle:NSLocalizedString(@"Ok",nil) block:^(){
linphone_call_set_authentication_token_verified(call, !valid);
[securitySheet release];
securitySheet = nil;
}];
[securitySheet addDestructiveButtonWithTitle:NSLocalizedString(@"Cancel",nil) block:^(){
[securitySheet release];
securitySheet = nil;
}];
[securitySheet showInView:[PhoneMainView instance].view];
}
}
}
}
[securitySheet addDestructiveButtonWithTitle:NSLocalizedString(@"Cancel",nil) block:^(){
[securitySheet release];
securitySheet = nil;
}];
[securitySheet showInView:[PhoneMainView instance].view];
}
}
}
}
}
-(void)actionSheet:(UIActionSheet *)actionSheet didDismissWithButtonIndex:(NSInteger)buttonIndex{
[securitySheet release];
securitySheet = nil;
[securitySheet release];
securitySheet = nil;
}
#pragma mark - TPMultiLayoutViewController Functions
- (NSDictionary*)attributesForView:(UIView*)view {
NSMutableDictionary *attributes = [NSMutableDictionary dictionary];
[attributes setObject:[NSValue valueWithCGRect:view.frame] forKey:@"frame"];
[attributes setObject:[NSValue valueWithCGRect:view.bounds] forKey:@"bounds"];
[attributes setObject:[NSNumber numberWithInteger:view.autoresizingMask] forKey:@"autoresizingMask"];
return attributes;
NSMutableDictionary *attributes = [NSMutableDictionary dictionary];
[attributes setObject:[NSValue valueWithCGRect:view.frame] forKey:@"frame"];
[attributes setObject:[NSValue valueWithCGRect:view.bounds] forKey:@"bounds"];
[attributes setObject:[NSNumber numberWithInteger:view.autoresizingMask] forKey:@"autoresizingMask"];
return attributes;
}
- (void)applyAttributes:(NSDictionary*)attributes toView:(UIView*)view {
view.frame = [[attributes objectForKey:@"frame"] CGRectValue];
view.bounds = [[attributes objectForKey:@"bounds"] CGRectValue];
view.autoresizingMask = [[attributes objectForKey:@"autoresizingMask"] integerValue];
view.frame = [[attributes objectForKey:@"frame"] CGRectValue];
view.bounds = [[attributes objectForKey:@"bounds"] CGRectValue];
view.autoresizingMask = [[attributes objectForKey:@"autoresizingMask"] integerValue];
}
@end

View file

@ -1,8 +1,8 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="4514" systemVersion="13A603" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none">
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="6245" systemVersion="13F34" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none">
<dependencies>
<deployment defaultVersion="1280" identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="3747"/>
<deployment defaultVersion="1536" identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="6238"/>
</dependencies>
<objects>
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner" customClass="UIStateBar">
@ -15,6 +15,7 @@
<outlet property="registrationStateImage" destination="5" id="14"/>
<outlet property="registrationStateLabel" destination="6" id="15"/>
<outlet property="view" destination="4" id="11"/>
<outlet property="voicemailCount" destination="jEB-96-YxX" id="hV2-9Z-i8b"/>
</connections>
</placeholder>
<placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
@ -69,8 +70,17 @@
<action selector="doSecurityClick:" destination="-1" eventType="touchUpInside" id="30"/>
</connections>
</button>
<label opaque="NO" userInteractionEnabled="NO" tag="7" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="VOICEMAIL MSGS" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" id="jEB-96-YxX" userLabel="voicemailCount">
<rect key="frame" x="156" y="1" width="88" height="21"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<color key="textColor" white="0.66666666666666663" alpha="1" colorSpace="calibratedWhite"/>
<nil key="highlightedColor"/>
</label>
</subviews>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="calibratedWhite"/>
<nil key="simulatedStatusBarMetrics"/>
<freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
</view>
<view contentMode="scaleToFill" id="19" userLabel="Landscape View">
<rect key="frame" x="0.0" y="0.0" width="480" height="23"/>
@ -114,12 +124,26 @@
<color key="titleColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
</state>
</button>
<label opaque="NO" userInteractionEnabled="NO" tag="7" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="VOICEMAIL MSGS" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" id="P9M-sM-t2B" userLabel="voicemailCount">
<rect key="frame" x="244" y="1" width="165" height="21"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<color key="textColor" white="0.66666666666666663" alpha="1" colorSpace="calibratedWhite"/>
<nil key="highlightedColor"/>
</label>
</subviews>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="calibratedWhite"/>
<nil key="simulatedStatusBarMetrics"/>
<freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
</view>
</objects>
<resources>
<image name="led_disconnected.png" width="18" height="17"/>
<image name="statebar_background.png" width="640" height="46"/>
</resources>
</document>
<simulatedMetricsContainer key="defaultSimulatedMetrics">
<simulatedStatusBarMetrics key="statusBar"/>
<simulatedOrientationMetrics key="orientation"/>
<simulatedScreenMetrics key="destination" type="retina4"/>
</simulatedMetricsContainer>
</document>