Commit 5c9edaab authored by Andreas Traczyk's avatar Andreas Traczyk Committed by Kateryna Kostiuk

messaging: redesign text entry

Change-Id: Ifebdddaee15894e38c9ebaf86528024887e7c7e0
Reviewed-by: Kateryna Kostiuk's avatarKateryna Kostiuk <kateryna.kostiuk@savoirfairelinux.com>
parent 9dff29d1
......@@ -249,6 +249,7 @@
5C093F011FB495830011D90E /* Differentiator.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 5C093F001FB495830011D90E /* Differentiator.framework */; };
5CE66F751FBF769B00EE9291 /* InitialLoadingViewController.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 5CE66F731FBF769B00EE9291 /* InitialLoadingViewController.storyboard */; };
5CE66F761FBF769B00EE9291 /* InitialLoadingViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5CE66F741FBF769B00EE9291 /* InitialLoadingViewController.swift */; };
62006E04203F4DD6003C3197 /* UITextField+Helpers.swift in Sources */ = {isa = PBXBuildFile; fileRef = 62006E03203F4DD6003C3197 /* UITextField+Helpers.swift */; };
621231F91F880EDF009B86F0 /* UILabel+Ring.swift in Sources */ = {isa = PBXBuildFile; fileRef = 621231F81F880EDF009B86F0 /* UILabel+Ring.swift */; };
621231FB1F8D6FEE009B86F0 /* MessageCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 621231FA1F8D6FEE009B86F0 /* MessageCell.swift */; };
623660AA20092081002598C1 /* src in Resources */ = {isa = PBXBuildFile; fileRef = 623660A920092081002598C1 /* src */; };
......@@ -542,6 +543,7 @@
5C093F001FB495830011D90E /* Differentiator.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Differentiator.framework; path = Carthage/Build/iOS/Differentiator.framework; sourceTree = "<group>"; };
5CE66F731FBF769B00EE9291 /* InitialLoadingViewController.storyboard */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.storyboard; path = InitialLoadingViewController.storyboard; sourceTree = "<group>"; };
5CE66F741FBF769B00EE9291 /* InitialLoadingViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = InitialLoadingViewController.swift; sourceTree = "<group>"; };
62006E03203F4DD6003C3197 /* UITextField+Helpers.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "UITextField+Helpers.swift"; sourceTree = "<group>"; };
621231F81F880EDF009B86F0 /* UILabel+Ring.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "UILabel+Ring.swift"; sourceTree = "<group>"; };
621231FA1F8D6FEE009B86F0 /* MessageCell.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MessageCell.swift; sourceTree = "<group>"; };
623660A920092081002598C1 /* src */ = {isa = PBXFileReference; lastKnownFileType = folder; name = src; path = ../../daemon/src; sourceTree = "<group>"; };
......@@ -845,6 +847,7 @@
0EE1B54D1F75ACDE00BA98EE /* CNContactVCardSerialization+Helpers.swift */,
621231F81F880EDF009B86F0 /* UILabel+Ring.swift */,
0EDCC85F1F98150500B121D7 /* UIView+Rx.swift */,
62006E03203F4DD6003C3197 /* UITextField+Helpers.swift */,
);
path = Extensions;
sourceTree = "<group>";
......@@ -1758,6 +1761,7 @@
1A5DC0241F3564360075E8EF /* ContactRequestModel.swift in Sources */,
0E4909701FEAC1C6005CAA50 /* CallModel.swift in Sources */,
1A5DC03F1F35678D0075E8EF /* ContactRequestsViewController.swift in Sources */,
62006E04203F4DD6003C3197 /* UITextField+Helpers.swift in Sources */,
1A20418B1F1EA58A00C08435 /* ViewModelBased.swift in Sources */,
1A5DC01E1F355DA70075E8EF /* ContactsAdapterDelegate.swift in Sources */,
0E983E6E1FC77C3E0082103E /* ConversationModel.swift in Sources */,
......
......@@ -65,6 +65,7 @@ enum Asset {
static let pauseCall = ImageAsset(name: "pause_call")
static let ringIcon = ImageAsset(name: "ringIcon")
static let ringLogo = ImageAsset(name: "ring_logo")
static let sendButton = ImageAsset(name: "send_button")
static let settingsIcon = ImageAsset(name: "settings_icon")
static let stopCall = ImageAsset(name: "stop_call")
static let switchCamera = ImageAsset(name: "switch_camera")
......@@ -95,6 +96,7 @@ enum Asset {
pauseCall,
ringIcon,
ringLogo,
sendButton,
settingsIcon,
stopCall,
switchCamera,
......
......@@ -33,8 +33,10 @@ extension UIColor {
static let ringSecondary = UIColor(red: 0, green: 76, blue: 96, alpha: 1.0)
static let ringMsgCellSent = UIColor(red: 58, green: 192, blue: 210, alpha: 1.0)
static let ringMsgCellSentText = UIColor(red: 255, green: 255, blue: 255, alpha: 1.0)
static let ringMsgCellReceived = UIColor(red: 235, green: 239, blue: 239, alpha: 1.0)
static let ringMsgCellReceived = UIColor(red: 231, green: 235, blue: 235, alpha: 1.0)
static let ringMsgCellReceivedText = UIColor(red: 48, green: 48, blue: 48, alpha: 1.0)
static let ringMsgCellTimeText = UIColor(red: 128, green: 128, blue: 128, alpha: 1.0)
static let ringMsgBackground = UIColor(red: 252, green: 252, blue: 252, alpha: 1.0)
static let ringMsgTextFieldBackground = UIColor(red: 252, green: 252, blue: 252, alpha: 1.0)
static let ringUITableViewCellSelection = UIColor(red: 209, green: 210, blue: 210, alpha: 1.0)
}
/*
* Copyright (C) 2017 Savoir-faire Linux Inc.
*
* Author: Andreas Traczyk <andreas.traczyk@savoirfairelinux.com>
*
* 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 3 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
import Foundation
extension UITextField {
func setPadding(_ left: CGFloat, _ right: CGFloat) {
self.leftView = UIView(frame: CGRect(x: 0, y: 0, width: left, height: self.frame.size.height))
self.rightView = UIView(frame: CGRect(x: 0, y: 0, width: right, height: self.frame.size.height))
self.leftViewMode = .always
self.rightViewMode = .always
}
}
......@@ -30,6 +30,7 @@ class MessageCell: UITableViewCell, NibReusable {
@IBOutlet weak var bubble: MessageBubble!
@IBOutlet weak var bubbleBottomConstraint: NSLayoutConstraint!
@IBOutlet weak var bubbleTopConstraint: NSLayoutConstraint!
@IBOutlet weak var messageLabelMarginConstraint: NSLayoutConstraint!
@IBOutlet weak var messageLabel: ActiveLabel!
@IBOutlet weak var bottomCorner: UIView!
@IBOutlet weak var topCorner: UIView!
......@@ -92,7 +93,7 @@ class MessageCell: UITableViewCell, NibReusable {
// setup the label
self.timeLabel.text = item.timeStringShown
self.timeLabel.textColor = UIColor.ringMsgCellTimeText
self.timeLabel.font = UIFont.boldSystemFont(ofSize: 14.0)
self.timeLabel.font = UIFont.systemFont(ofSize: 12.0, weight: UIFont.Weight.medium)
// show the time
self.timeLabel.isHidden = false
......@@ -170,6 +171,7 @@ class MessageCell: UITableViewCell, NibReusable {
func configureFromItem(_ conversationViewModel: ConversationViewModel,
_ items: [MessageViewModel]?,
cellForRowAt indexPath: IndexPath) {
self.backgroundColor = UIColor.clear
guard let item = items?[indexPath.row] else {
return
}
......@@ -181,7 +183,12 @@ class MessageCell: UITableViewCell, NibReusable {
self.bubble.backgroundColor = UIColor.ringMsgCellReceived
self.messageLabel.setTextWithLineSpacing(withText: item.content, withLineSpacing: 2)
// generated messages should always show the time
self.bubbleTopConstraint.constant = 32
if indexPath.row == 0 {
messageLabelMarginConstraint.constant = 4
self.bubbleTopConstraint.constant = 36
} else {
self.bubbleTopConstraint.constant = 32
}
return
}
......@@ -190,7 +197,8 @@ class MessageCell: UITableViewCell, NibReusable {
// special cases where top/bottom margins should be larger
if indexPath.row == 0 {
self.bubbleTopConstraint.constant = 32
messageLabelMarginConstraint.constant = 4
self.bubbleTopConstraint.constant = 36
} else if items?.count == indexPath.row + 1 {
self.bubbleBottomConstraint.constant = 16
}
......
<?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="13196" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES">
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="13771" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES">
<device id="retina4_7" orientation="portrait">
<adaptation id="fullscreen"/>
</device>
<dependencies>
<deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="13174"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="13772"/>
<capability name="Constraints to layout margins" minToolsVersion="6.0"/>
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
</dependencies>
......@@ -25,7 +25,6 @@
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Label Label Label Label " textAlignment="center" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="ijf-jY-sqW">
<rect key="frame" x="161.5" y="4" width="155.5" height="22.5"/>
<fontDescription key="fontDescription" type="system" pointSize="14"/>
<color key="textColor" white="0.0" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<nil key="highlightedColor"/>
</label>
</subviews>
......@@ -43,21 +42,21 @@
</userDefinedRuntimeAttributes>
</view>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="11/14/2016 12:34PM" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="4OM-U1-teG" userLabel="Message Time">
<rect key="frame" x="178" y="6" width="154" height="21"/>
<color key="backgroundColor" red="1" green="1" blue="1" alpha="1" colorSpace="calibratedRGB"/>
<rect key="frame" x="178" y="9" width="154" height="21"/>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<nil key="textColor"/>
<nil key="highlightedColor"/>
</label>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="Wm5-ce-Sf6" userLabel="Left Divider">
<rect key="frame" x="16" y="16" width="146" height="1"/>
<rect key="frame" x="16" y="19" width="146" height="1"/>
<color key="backgroundColor" red="0.94117647059999998" green="0.94117647059999998" blue="0.94117647059999998" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstAttribute="height" constant="1" id="dEi-Ni-etd"/>
</constraints>
</view>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="WgT-u7-Mgl" userLabel="Right Divider">
<rect key="frame" x="348" y="16" width="138" height="1"/>
<rect key="frame" x="348" y="19" width="126" height="1"/>
<color key="backgroundColor" red="0.94117647059999998" green="0.94117647059999998" blue="0.94117647059999998" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstAttribute="height" constant="1" id="9kZ-1u-mwB"/>
......@@ -87,6 +86,7 @@
<outlet property="bubbleTopConstraint" destination="R6Q-PY-A3m" id="IQA-QC-eV0"/>
<outlet property="leftDivider" destination="Wm5-ce-Sf6" id="EaQ-1G-8Db"/>
<outlet property="messageLabel" destination="ijf-jY-sqW" id="Wcu-8D-wWf"/>
<outlet property="messageLabelMarginConstraint" destination="CbK-m1-TUR" id="8qD-tP-8QW"/>
<outlet property="rightDivider" destination="WgT-u7-Mgl" id="k10-3V-ZLw"/>
<outlet property="timeLabel" destination="4OM-U1-teG" id="ub4-Z8-CsM"/>
</connections>
......
......@@ -28,42 +28,42 @@
</constraints>
</view>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="WBd-CS-7Qv" userLabel="Top Corner">
<rect key="frame" x="64" y="8" width="15" height="15"/>
<rect key="frame" x="64" y="8" width="17" height="17"/>
<color key="backgroundColor" red="1" green="0.0" blue="1" alpha="1" colorSpace="calibratedRGB"/>
<constraints>
<constraint firstAttribute="height" constant="15" id="fjJ-O1-VNm"/>
<constraint firstAttribute="width" constant="15" id="gch-Wg-ytg"/>
<constraint firstAttribute="height" constant="17" id="fjJ-O1-VNm"/>
<constraint firstAttribute="width" constant="17" id="gch-Wg-ytg"/>
</constraints>
</view>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="XcL-CH-BiH" userLabel="Bottom Corner">
<rect key="frame" x="64" y="24" width="15" height="15"/>
<rect key="frame" x="64" y="22" width="17" height="17"/>
<color key="backgroundColor" red="1" green="0.5" blue="0.0" alpha="1" colorSpace="calibratedRGB"/>
<constraints>
<constraint firstAttribute="width" constant="15" id="ocR-DU-zKZ"/>
<constraint firstAttribute="height" constant="15" id="ooc-tv-fiO"/>
<constraint firstAttribute="width" constant="17" id="ocR-DU-zKZ"/>
<constraint firstAttribute="height" constant="17" id="ooc-tv-fiO"/>
</constraints>
</view>
<view clipsSubviews="YES" contentMode="scaleToFill" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="kZJ-Ay-LTR" customClass="MessageBubble" customModule="Ring" customModuleProvider="target">
<rect key="frame" x="64" y="8" width="190.5" height="30.5"/>
<rect key="frame" x="64" y="8" width="198.5" height="30.5"/>
<subviews>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Label Label Label Label" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="lyR-7c-S2k" customClass="ActiveLabel" customModule="ActiveLabel">
<rect key="frame" x="10" y="8" width="170.5" height="14.5"/>
<rect key="frame" x="14" y="7" width="170.5" height="16.5"/>
<fontDescription key="fontDescription" type="system" pointSize="16"/>
<nil key="highlightedColor"/>
</label>
</subviews>
<color key="backgroundColor" red="0.66666666666666663" green="0.66666666666666663" blue="0.66666666666666663" alpha="1" colorSpace="calibratedRGB"/>
<constraints>
<constraint firstAttribute="height" relation="greaterThanOrEqual" constant="30" id="1Kj-UZ-gu7"/>
<constraint firstItem="lyR-7c-S2k" firstAttribute="leading" secondItem="kZJ-Ay-LTR" secondAttribute="leading" constant="10" id="8m5-sR-xnh"/>
<constraint firstAttribute="width" relation="greaterThanOrEqual" constant="28" id="UWN-H4-Sh9"/>
<constraint firstAttribute="bottom" secondItem="lyR-7c-S2k" secondAttribute="bottom" constant="8" id="gwN-uX-PWd"/>
<constraint firstAttribute="trailing" secondItem="lyR-7c-S2k" secondAttribute="trailing" constant="10" id="uzV-kG-oGN"/>
<constraint firstItem="lyR-7c-S2k" firstAttribute="top" secondItem="kZJ-Ay-LTR" secondAttribute="top" constant="8" id="ycc-WI-Jk6"/>
<constraint firstAttribute="height" relation="greaterThanOrEqual" constant="31" id="1Kj-UZ-gu7"/>
<constraint firstItem="lyR-7c-S2k" firstAttribute="leading" secondItem="kZJ-Ay-LTR" secondAttribute="leading" constant="14" id="8m5-sR-xnh"/>
<constraint firstAttribute="width" relation="greaterThanOrEqual" constant="34" id="UWN-H4-Sh9"/>
<constraint firstAttribute="bottom" secondItem="lyR-7c-S2k" secondAttribute="bottom" constant="7" id="gwN-uX-PWd"/>
<constraint firstAttribute="trailing" secondItem="lyR-7c-S2k" secondAttribute="trailing" constant="14" id="uzV-kG-oGN"/>
<constraint firstItem="lyR-7c-S2k" firstAttribute="top" secondItem="kZJ-Ay-LTR" secondAttribute="top" constant="7" id="ycc-WI-Jk6"/>
</constraints>
<userDefinedRuntimeAttributes>
<userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
<integer key="value" value="15"/>
<real key="value" value="17"/>
</userDefinedRuntimeAttribute>
</userDefinedRuntimeAttributes>
</view>
......@@ -83,7 +83,7 @@
</view>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="11/14/2016 12:34PM" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="mhg-uK-iD9" userLabel="Message Time">
<rect key="frame" x="178.5" y="9" width="154" height="21"/>
<color key="backgroundColor" red="1" green="1" blue="1" alpha="1" colorSpace="calibratedRGB"/>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<nil key="textColor"/>
<nil key="highlightedColor"/>
......
......@@ -20,43 +20,55 @@
<autoresizingMask key="autoresizingMask"/>
<subviews>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="hdz-AQ-xHI" userLabel="Bottom Corner">
<rect key="frame" x="479" y="24" width="15" height="15"/>
<rect key="frame" x="477" y="22" width="17" height="17"/>
<color key="backgroundColor" red="1" green="0.5" blue="0.0" alpha="1" colorSpace="calibratedRGB"/>
<constraints>
<constraint firstAttribute="height" constant="15" id="D0h-cW-9kB"/>
<constraint firstAttribute="width" constant="15" id="wlh-ar-Nsv"/>
<constraint firstAttribute="height" constant="17" id="D0h-cW-9kB"/>
<constraint firstAttribute="width" constant="17" id="wlh-ar-Nsv"/>
</constraints>
<userDefinedRuntimeAttributes>
<userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
<real key="value" value="0.0"/>
</userDefinedRuntimeAttribute>
<userDefinedRuntimeAttribute type="boolean" keyPath="roundedCorners" value="NO"/>
</userDefinedRuntimeAttributes>
</view>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="EMh-bG-ilg" userLabel="Top Corner">
<rect key="frame" x="479" y="8" width="15" height="15"/>
<rect key="frame" x="477" y="8" width="17" height="17"/>
<color key="backgroundColor" red="1" green="0.0" blue="1" alpha="1" colorSpace="calibratedRGB"/>
<constraints>
<constraint firstAttribute="width" constant="15" id="zaa-Rn-ziw"/>
<constraint firstAttribute="height" constant="15" id="zuP-4P-1GS"/>
<constraint firstAttribute="width" constant="17" id="zaa-Rn-ziw"/>
<constraint firstAttribute="height" constant="17" id="zuP-4P-1GS"/>
</constraints>
<userDefinedRuntimeAttributes>
<userDefinedRuntimeAttribute type="boolean" keyPath="roundedCorners" value="NO"/>
<userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
<real key="value" value="0.0"/>
</userDefinedRuntimeAttribute>
</userDefinedRuntimeAttributes>
</view>
<view clipsSubviews="YES" contentMode="scaleToFill" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="kZJ-Ay-LTR" customClass="MessageBubble" customModule="Ring" customModuleProvider="target">
<rect key="frame" x="303.5" y="8" width="190.5" height="31"/>
<rect key="frame" x="286.5" y="8" width="207.5" height="31"/>
<subviews>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Label Label Label Label" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="lyR-7c-S2k" customClass="ActiveLabel" customModule="ActiveLabel">
<rect key="frame" x="10" y="8" width="170.5" height="15"/>
<fontDescription key="fontDescription" name=".AppleSystemUIFont" family=".AppleSystemUIFont" pointSize="16"/>
<rect key="frame" x="14" y="7" width="179.5" height="17"/>
<fontDescription key="fontDescription" name=".AppleSystemUIFont" family=".AppleSystemUIFont" pointSize="17"/>
<color key="textColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
<nil key="highlightedColor"/>
</label>
</subviews>
<color key="backgroundColor" red="0.66666666666666663" green="0.66666666666666663" blue="0.66666666666666663" alpha="1" colorSpace="calibratedRGB"/>
<constraints>
<constraint firstAttribute="height" relation="greaterThanOrEqual" constant="30" id="1Kj-UZ-gu7"/>
<constraint firstItem="lyR-7c-S2k" firstAttribute="leading" secondItem="kZJ-Ay-LTR" secondAttribute="leading" constant="10" id="8m5-sR-xnh"/>
<constraint firstAttribute="width" relation="greaterThanOrEqual" constant="28" id="BZE-kP-hPK"/>
<constraint firstAttribute="bottom" secondItem="lyR-7c-S2k" secondAttribute="bottom" constant="8" id="gwN-uX-PWd"/>
<constraint firstAttribute="trailing" secondItem="lyR-7c-S2k" secondAttribute="trailing" constant="10" id="uzV-kG-oGN"/>
<constraint firstItem="lyR-7c-S2k" firstAttribute="top" secondItem="kZJ-Ay-LTR" secondAttribute="top" constant="8" id="ycc-WI-Jk6"/>
<constraint firstAttribute="height" relation="greaterThanOrEqual" constant="31" id="1Kj-UZ-gu7"/>
<constraint firstItem="lyR-7c-S2k" firstAttribute="leading" secondItem="kZJ-Ay-LTR" secondAttribute="leading" constant="14" id="8m5-sR-xnh"/>
<constraint firstAttribute="width" relation="greaterThanOrEqual" constant="34" id="BZE-kP-hPK"/>
<constraint firstAttribute="bottom" secondItem="lyR-7c-S2k" secondAttribute="bottom" constant="7" id="gwN-uX-PWd"/>
<constraint firstAttribute="trailing" secondItem="lyR-7c-S2k" secondAttribute="trailing" constant="14" id="uzV-kG-oGN"/>
<constraint firstItem="lyR-7c-S2k" firstAttribute="top" secondItem="kZJ-Ay-LTR" secondAttribute="top" constant="7" id="ycc-WI-Jk6"/>
</constraints>
<userDefinedRuntimeAttributes>
<userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
<integer key="value" value="15"/>
<real key="value" value="17"/>
</userDefinedRuntimeAttribute>
</userDefinedRuntimeAttributes>
</view>
......@@ -81,10 +93,10 @@
<nil key="highlightedColor"/>
</label>
<activityIndicatorView opaque="NO" contentMode="scaleToFill" horizontalHuggingPriority="750" verticalHuggingPriority="750" hidesWhenStopped="YES" animating="YES" style="gray" translatesAutoresizingMaskIntoConstraints="NO" id="78h-fZ-7yf" userLabel="Sending Indicator">
<rect key="frame" x="275.5" y="16" width="20" height="20"/>
<rect key="frame" x="258.5" y="16" width="20" height="20"/>
</activityIndicatorView>
<label hidden="YES" opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Failed" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="P5a-HI-uhr" userLabel="Failed Status Label">
<rect key="frame" x="253" y="16" width="42.5" height="19.5"/>
<rect key="frame" x="236" y="16" width="42.5" height="19.5"/>
<fontDescription key="fontDescription" type="system" pointSize="16"/>
<color key="textColor" red="0.94117647058823528" green="0.0" blue="0.0" alpha="1" colorSpace="calibratedRGB"/>
<nil key="highlightedColor"/>
......
<?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="12121" systemVersion="16F73" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES" initialViewController="O1m-sW-gim">
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="13771" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="O1m-sW-gim">
<device id="retina4_7" orientation="portrait">
<adaptation id="fullscreen"/>
</device>
<dependencies>
<deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="12089"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="13772"/>
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
</dependencies>
<scenes>
......@@ -13,10 +14,6 @@
<scene sceneID="2Fj-m2-pCD">
<objects>
<viewController hidesBottomBarWhenPushed="YES" id="O1m-sW-gim" customClass="ConversationViewController" customModule="Ring" customModuleProvider="target" sceneMemberID="viewController">
<layoutGuides>
<viewControllerLayoutGuide type="top" id="Hdp-cb-K7b"/>
<viewControllerLayoutGuide type="bottom" id="zju-EL-lSj"/>
</layoutGuides>
<view key="view" contentMode="scaleToFill" id="lhx-ny-Zct">
<rect key="frame" x="0.0" y="0.0" width="375" height="667"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
......@@ -52,15 +49,16 @@
</subviews>
<color key="backgroundColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
<constraints>
<constraint firstItem="6Wq-EJ-CAF" firstAttribute="leading" secondItem="lhx-ny-Zct" secondAttribute="leading" id="5VA-aR-jIL"/>
<constraint firstAttribute="trailing" secondItem="yc2-Jn-6vm" secondAttribute="trailing" id="6Ar-yh-iTT"/>
<constraint firstItem="6Wq-EJ-CAF" firstAttribute="leading" secondItem="mrp-Ty-hZO" secondAttribute="leading" id="5VA-aR-jIL"/>
<constraint firstItem="mrp-Ty-hZO" firstAttribute="trailing" secondItem="yc2-Jn-6vm" secondAttribute="trailing" id="6Ar-yh-iTT"/>
<constraint firstAttribute="bottom" secondItem="6Wq-EJ-CAF" secondAttribute="bottom" id="QKw-Wp-ff0"/>
<constraint firstItem="yc2-Jn-6vm" firstAttribute="top" secondItem="lhx-ny-Zct" secondAttribute="top" id="Qd0-eb-gyZ"/>
<constraint firstAttribute="trailing" secondItem="6Wq-EJ-CAF" secondAttribute="trailing" id="W84-gc-kua"/>
<constraint firstItem="yc2-Jn-6vm" firstAttribute="leading" secondItem="lhx-ny-Zct" secondAttribute="leading" id="Wzk-uM-Oge"/>
<constraint firstAttribute="bottom" secondItem="yc2-Jn-6vm" secondAttribute="bottom" id="m6U-Gp-jhl"/>
<constraint firstItem="mrp-Ty-hZO" firstAttribute="trailing" secondItem="6Wq-EJ-CAF" secondAttribute="trailing" id="W84-gc-kua"/>
<constraint firstItem="yc2-Jn-6vm" firstAttribute="leading" secondItem="mrp-Ty-hZO" secondAttribute="leading" id="Wzk-uM-Oge"/>
<constraint firstItem="mrp-Ty-hZO" firstAttribute="bottom" secondItem="yc2-Jn-6vm" secondAttribute="bottom" id="m6U-Gp-jhl"/>
<constraint firstItem="6Wq-EJ-CAF" firstAttribute="top" secondItem="lhx-ny-Zct" secondAttribute="top" id="v3Q-NK-vb1"/>
</constraints>
<viewLayoutGuide key="safeArea" id="mrp-Ty-hZO"/>
</view>
<extendedEdge key="edgesForExtendedLayout"/>
<connections>
......
......@@ -23,15 +23,6 @@ import RxSwift
import Reusable
import SwiftyBeaver
extension UITextField {
func setPadding(_ left: CGFloat, _ right: CGFloat) {
self.leftView = UIView(frame: CGRect(x: 0, y: 0, width: left, height: self.frame.size.height))
self.rightView = UIView(frame: CGRect(x: 0, y: 0, width: right, height: self.frame.size.height))
self.leftViewMode = .always
self.rightViewMode = .always
}
}
class ConversationViewController: UIViewController, UITextFieldDelegate, StoryboardBased, ViewModelBased {
let log = SwiftyBeaver.self
......@@ -54,36 +45,43 @@ class ConversationViewController: UIViewController, UITextFieldDelegate, Storybo
self.setupTableView()
self.setupBindings()
self.messageAccessoryView.messageTextField.delegate = self
self.messageAccessoryView.messageTextField.setPadding(8.0, 8.0)
/*
Register to keyboard notifications to adjust tableView insets when the keybaord appears
or disappears
*/
NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillShow(withNotification:)), name: NSNotification.Name.UIKeyboardWillShow, object: nil)
NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillHide(withNotification:)), name: NSNotification.Name.UIKeyboardWillHide, object: nil)
let tap: UITapGestureRecognizer = UITapGestureRecognizer(target: self, action: #selector(ConversationViewController.dismissKeyboard))
view.addGestureRecognizer(tap)
}
@objc func keyboardWillShow(withNotification notification: Notification) {
@objc func dismissKeyboard() {
self.becomeFirstResponder()
}
@objc func keyboardWillShow(withNotification notification: Notification) {
let userInfo: Dictionary = notification.userInfo!
guard let keyboardFrame: NSValue = userInfo[UIKeyboardFrameEndUserInfoKey] as? NSValue else { return }
let keyboardRectangle = keyboardFrame.cgRectValue
let keyboardHeight = keyboardRectangle.height
self.tableView.contentInset.bottom = keyboardHeight
self.tableView.scrollIndicatorInsets.bottom = keyboardHeight
var heightOffset = CGFloat(0.0)
if keyboardHeight != self.messageAccessoryView.frame.height {
heightOffset = -24.0
}
self.tableView.contentInset.bottom = keyboardHeight + heightOffset
self.tableView.scrollIndicatorInsets.bottom = keyboardHeight + heightOffset
self.scrollToBottom(animated: false)
self.updateBottomOffset()
}
@objc func keyboardWillHide(withNotification notification: Notification) {
self.tableView.contentInset.bottom = 0
self.tableView.scrollIndicatorInsets.bottom = 0
self.tableView.contentInset.bottom = self.messageAccessoryView.frame.height
self.tableView.scrollIndicatorInsets.bottom = self.messageAccessoryView.frame.height
self.updateBottomOffset()
}
......@@ -136,6 +134,13 @@ class ConversationViewController: UIViewController, UITextFieldDelegate, Storybo
}
func setupUI() {
self.messageAccessoryView.messageTextField.delegate = self
self.messageAccessoryView.messageTextField.setPadding(8.0, 8.0)
self.tableView.backgroundColor = UIColor.ringMsgBackground
self.messageAccessoryView.backgroundColor = UIColor.ringMsgTextFieldBackground
self.view.backgroundColor = UIColor.ringMsgTextFieldBackground
if UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiom.pad {
self.viewModel.userName.asObservable().bind(to: self.navigationItem.rx.title).disposed(by: disposeBag)
} else {
......@@ -330,12 +335,13 @@ class ConversationViewController: UIViewController, UITextFieldDelegate, Storybo
}()
func setupBindings() {
//Binds the keyboard Send button action to the ViewModel
self.messageAccessoryView.messageTextField.rx.controlEvent(.editingDidEndOnExit).subscribe(onNext: { [unowned self] _ in
self.viewModel.sendMessage(withContent: self.messageAccessoryView.messageTextField.text!)
guard let payload = self.messageAccessoryView.messageTextField.text, !payload.isEmpty else {
return
}
self.viewModel.sendMessage(withContent: payload)
self.messageAccessoryView.messageTextField.text = ""
}).disposed(by: disposeBag)
}).disposed(by: self.disposeBag)
}
// Avoid the keyboard to be hidden when the Send button is touched
......
......@@ -24,6 +24,7 @@ import Reusable
class MessageAccessoryView: UIView, NibLoadable {
@IBOutlet weak var messageTextField: UITextField!
@IBOutlet weak var sendButton: UIButton!
override open func didMoveToWindow() {
super.didMoveToWindow()
......
<?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="13196" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES">
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="13771" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES">
<device id="retina4_7" orientation="portrait">
<adaptation id="fullscreen"/>
</device>
<dependencies>
<deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="13174"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="13772"/>
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
</dependencies>
<objects>
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
<placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
<view contentMode="scaleToFill" id="Fja-dy-lIy" customClass="MessageAccessoryView" customModule="Ring" customModuleProvider="target">
<rect key="frame" x="0.0" y="0.0" width="315" height="54"/>
<rect key="frame" x="0.0" y="0.0" width="315" height="58"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<subviews>
<textField opaque="NO" clipsSubviews="YES" contentMode="scaleToFill" contentHorizontalAlignment="left" contentVerticalAlignment="center" borderStyle="roundedRect" placeholder="type your message..." textAlignment="natural" minimumFontSize="17" translatesAutoresizingMaskIntoConstraints="NO" id="AJA-0c-Rp7">
<rect key="frame" x="16" y="8" width="283" height="30"/>
<rect key="frame" x="16" y="12" width="287" height="34"/>
<nil key="textColor"/>
<fontDescription key="fontDescription" type="system" pointSize="15"/>
<textInputTraits key="textInputTraits" returnKeyType="send" enablesReturnKeyAutomatically="YES"/>
<userDefinedRuntimeAttributes>
<userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
<integer key="value" value="15"/>
<real key="value" value="17"/>
</userDefinedRuntimeAttribute>
<userDefinedRuntimeAttribute type="color" keyPath="borderColor">
<color key="value" red="0.81568627450980391" green="0.81568627450980391" blue="0.81568627450980391" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<color key="value" red="0.93333333333333335" green="0.93333333333333335" blue="0.93333333333333335" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
</userDefinedRuntimeAttribute>
<userDefinedRuntimeAttribute type="number" keyPath="borderWidth">