有没有办法在没有任何第三方库的IOS Swift中实现Slide Sidebar Menu(如Facebook应用程序)?我寻找解决方案,但我只创建了在Objective-C中实现的这个功能.
Ily*_*kin 17
我相信你可以从iOS8中大幅更新的UISplitViewController开始.观看会话查看iOS8中的控制器进度和使用UIKit构建自适应应用程序以 获取详细信息.它们提供了第二个会话的代码示例(但不是第一个会话形式:/).在这一点上,我很自然地在iOS8中基于分割视图控制器制作这种UI.
更新:看起来并非他们所讨论的所有API都已登陆.例如,在视频中提到的当前beta4中没有提供BarsOnSwipe.
Rob*_*hen 16
更新:请考虑使用我更新的答案,而不是这个.Scrollview/Container View方法有很多边缘情况,可以通过使用自定义视图控制器转换来避免.
我到处寻找一个不需要库的Swift菜单解决方案.结束创建我自己的教程,这与Fengson的方法非常相似:
以下是一些要点:
scrollview将处理菜单滑动动作以及平移手势container视图并排放置在内部scrollview.容器允许您嵌入顶级控制器.scrollview,设置paging enabled但禁用bounces.这将迫使滑道进入打开或关闭状态embed一个UITableViewController在左容器embeda UITabBarController在正确的容器中container,添加layer.shadowOpacity0.8 的运行时属性.这为您提供了一个没有任何代码的免费阴影分隔符NSNotificationCenter用来与之沟通scrollviewscrollView.setContentOffset.x处理菜单的实际打开和关闭这是一个带有左侧滑出菜单的标签栏应用程序的工作示例项目,包括屏幕截图和说明.
https://github.com/ThornTechPublic/LeftSlideoutMenu
以及它如何工作的更通用的解释:
http://www.thorntech.com/2015/06/want-to-implement-a-slideout-menu-in-your-swift-app-heres-how/
滑动侧栏菜单,适用于iOS7和iOS8,Swift编码.
如果你想在NavigationController级别(它意味着,对于它后面的视图控制器):
https://github.com/evnaz/ENSwiftSideMenu
如果你只想在一个ViewController中:
视频:https://www.youtube.com/watch?v = qaLiZgUK2T0
源代码:http://goo.gl/ULWxJh
在这种情况下,对于iOS7兼容性,只需添加此"if"条件,其中放置"添加模糊视图"注释,如下所示:
if (NSClassFromString("UIVisualEffectView") != nil) {
// Add blur view
let blurView:UIVisualEffectView = UIVisualEffectView(effect: UIBlurEffect(style: UIBlurEffectStyle.Light))
blurView.frame = sideBarContainerView.bounds
sideBarContainerView.addSubview(blurView)
}
Run Code Online (Sandbox Code Playgroud)
我认为使用自定义视图控制器转换是制作滑出菜单的可靠方法:
自定义视图控制器转换起初很难学习(至少对我来说是这样).我写了一篇关于如何创建交互式幻灯片菜单的博客文章,并尽力使其尽可能易于理解.
在很高的层次上,这就是它的工作原理:
UIViewControllerAnimatedTransitioning协议关闭过渡.您可以使用快照在动画期间表示主视图控制器.UIPercentDrivenInteractiveTransition对象,以使过渡与用户的移动保持同步.UIViewControllerTransitioningDelegate协议并连接所有自定义动画和交互式过渡.我实际上在此线程上有一个使用Scrollview/Container View的先前答案.这种方法适用于原型,但在准备好应用程序生产时会遇到很多边缘情况和错误.每周花在回应博客评论和修复边缘案例上的动机促使我写了关于这个主题的第二篇博文.
小智 6
这是我添加到混音中的另一个SideMenu库:https://github.com/jonkykong/SideMenu.
由Facebook启发的Swift iOS简单侧边菜单控件.左右两侧.无需编码.
- 它可以在故事板中实现,而无需一行代码.
- 四种标准动画风格可供选择(如果你想变得奇怪,甚至是视差).
- 高度可定制,无需编写大量自定义代码.
- 支持在单个手势中在两侧的侧面菜单之间连续滑动.
- 全局菜单配置.设置一次并完成所有屏幕.
- 菜单可以与任何其他View Controller一样显示和解除,因为此控件使用自定义转换.
这是我如何做的一个小例子,这个抽屉控件有左,中,右的uiview控制器.这个工作就像Slack IPad应用程序,其中一方或另一方是打开的.
/*
To use simply instantiate SlidingDrawerController as your root view in your AppDelegate, or in the
StoryBoard.
Once SlidingDrawerController is instantiated, set the drawerSize of the SlidingDrawerController,
and its leftViewControllerIdentifier, centerViewControllerIdentifier, and
rightViewControllerIdentifier to the Storyboard Identifier of the UIViewController
you want in the different locations.
*/
class SlidingDrawerController: UIViewController {
var drawerSize:CGFloat = 4.0
var leftViewControllerIdentifier:String = "leftViewController"
var centerViewControllerIdentifier:String = "centerViewController"
var rightViewControllerIdentifier:String = "rightViewController"
enum Drawers {
case left
case right
}
private var _leftViewController:UIViewController?
var leftViewController:UIViewController {
get{
if let vc = _leftViewController {
return vc;
}
return UIViewController();
}
}
private var _centerViewController:UIViewController?
var centerViewController:UIViewController {
get{
if let vc = _centerViewController {
return vc;
}
return UIViewController();
}
}
private var _rightViewController:UIViewController?
var rightViewController:UIViewController {
get{
if let vc = _rightViewController {
return vc;
}
return UIViewController();
}
}
static let SlidingDrawerOpenLeft = 1
static let SlidingDrawerOpenRight = 2
var openSide:SlidingDrawerController.Drawers {
get{
return _openSide;
}
}
private var _openSide = SlidingDrawerController.Drawers.left
override func viewDidLoad() {
super.viewDidLoad()
// Instantiate VC's with storyboard ID's
self._leftViewController = self.instantiateViewControllers(storyboardID: self.leftViewControllerIdentifier)
self._centerViewController = self.instantiateViewControllers(storyboardID: self.centerViewControllerIdentifier)
self._rightViewController = self.instantiateViewControllers(storyboardID: self.rightViewControllerIdentifier)
self.drawDrawers(size: UIScreen.main.bounds.size)
self.view.addSubview(self.leftViewController.view)
self.view.addSubview(self.centerViewController.view)
self.view.addSubview(self.rightViewController.view)
}
override func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) {
coordinator.animateAlongsideTransition(in: self.view, animation: { (UIViewControllerTransitionCoordinatorContext) -> Void in
// This is for beginning of transition
self.drawDrawers(size: size)
}, completion: { (UIViewControllerTransitionCoordinatorContext) -> Void in
// This is for after transition has completed.
})
}
// MARK: - Drawing View
func drawDrawers(size:CGSize) {
// Calculate Center View's Size
let centerWidth = (size.width/drawerSize) * (drawerSize - 1)
// Left Drawer
self.leftViewController.view.frame = CGRect(x: 0.0, y: 0.0, width: size.width/self.drawerSize, height: size.height)
// Center Drawer
self.centerViewController.view.frame = CGRect(x: self.leftViewController.view.frame.width, y: 0.0, width: centerWidth, height: size.height)
// Right Drawer
self.rightViewController.view.frame = CGRect(x: self.centerViewController.view.frame.origin.x + self.centerViewController.view.frame.size.width, y: 0.0, width: size.width/self.drawerSize, height: size.height)
// Capture the Swipes
let swipeRight = UISwipeGestureRecognizer(target: self, action: #selector(self.swipeRightAction(rec:)))
swipeRight.direction = .right
centerViewController.view.addGestureRecognizer(swipeRight)
let swipeLeft = UISwipeGestureRecognizer(target: self, action: #selector(self.swipeLeftAction(rec:)))
swipeLeft.direction = .left
centerViewController.view.addGestureRecognizer(swipeLeft)
openDrawer(openSide)
}
// MARK: - Open Drawers
func openDrawer(_ side:Drawers) {
self._openSide = side
var rect:CGRect
switch side{
case .left:
rect = CGRect(
x: 0.0,
y: 0.0,
width: self.view.bounds.width,
height: self.view.bounds.height
)
case .right:
rect = CGRect(
x: self.view.bounds.origin.x - self.leftViewController.view.bounds.size.width,
y: 0.0,
width: self.view.bounds.width,
height: self.view.bounds.height
)
}
UIView.animate(withDuration: 0.1, delay: 0, options: UIViewAnimationOptions.curveEaseIn, animations:
{ () -> Void in
// move views here
self.view.frame = rect
}, completion:
{ finished in
})
}
// MARK: - Swipe Handling
@objc func swipeRightAction(rec: UISwipeGestureRecognizer){
self.openDrawer(.left)
}
@objc func swipeLeftAction(rec:UISwipeGestureRecognizer){
self.openDrawer(.right)
}
// MARK: - Helpers
func instantiateViewControllers(storyboardID: String) -> UIViewController {
return UIStoryboard(name: "Main", bundle: nil)
.instantiateViewController(withIdentifier: "\(storyboardID)")
}
}
Run Code Online (Sandbox Code Playgroud)
来源于此.
图片在这里.
视频在这里.