在实际项目中你或许会遇到在一个集合视图中移动一项到另外一个位置,那么此时我们需要对视图中的元素进行重新排序,今天推荐一个很好用的第三方类LXReorderableCollectionViewFlowLayout【点此链接进入GITHUB

下面附上实现代码

//
// LXReorderableCollectionViewFlowLayout.h
//
// Created by Stan Chang Khin Boon on 1/10/12.
// Copyright (c) 2012 d--buzz. All rights reserved.
// #import <UIKit/UIKit.h> @interface LXReorderableCollectionViewFlowLayout : UICollectionViewFlowLayout <UIGestureRecognizerDelegate> @property (assign, nonatomic) CGFloat scrollingSpeed;
@property (assign, nonatomic) UIEdgeInsets scrollingTriggerEdgeInsets;
@property (strong, nonatomic, readonly) UILongPressGestureRecognizer *longPressGestureRecognizer;
@property (strong, nonatomic, readonly) UIPanGestureRecognizer *panGestureRecognizer; - (void)setUpGestureRecognizersOnCollectionView __attribute__((deprecated("Calls to setUpGestureRecognizersOnCollectionView method are not longer needed as setup are done automatically through KVO."))); @end @protocol LXReorderableCollectionViewDataSource <UICollectionViewDataSource> @optional - (void)collectionView:(UICollectionView *)collectionView itemAtIndexPath:(NSIndexPath *)fromIndexPath willMoveToIndexPath:(NSIndexPath *)toIndexPath;
- (void)collectionView:(UICollectionView *)collectionView itemAtIndexPath:(NSIndexPath *)fromIndexPath didMoveToIndexPath:(NSIndexPath *)toIndexPath; - (BOOL)collectionView:(UICollectionView *)collectionView canMoveItemAtIndexPath:(NSIndexPath *)indexPath;
- (BOOL)collectionView:(UICollectionView *)collectionView itemAtIndexPath:(NSIndexPath *)fromIndexPath canMoveToIndexPath:(NSIndexPath *)toIndexPath; @end @protocol LXReorderableCollectionViewDelegateFlowLayout <UICollectionViewDelegateFlowLayout>
@optional - (void)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout willBeginDraggingItemAtIndexPath:(NSIndexPath *)indexPath;
- (void)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout didBeginDraggingItemAtIndexPath:(NSIndexPath *)indexPath;
- (void)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout willEndDraggingItemAtIndexPath:(NSIndexPath *)indexPath;
- (void)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout didEndDraggingItemAtIndexPath:(NSIndexPath *)indexPath; @end

LXReorderableCollectionViewFlowLayout.h

//
// LXReorderableCollectionViewFlowLayout.m
//
// Created by Stan Chang Khin Boon on 1/10/12.
// Copyright (c) 2012 d--buzz. All rights reserved.
// #import "LXReorderableCollectionViewFlowLayout.h"
#import <QuartzCore/QuartzCore.h>
#import <objc/runtime.h> #define LX_FRAMES_PER_SECOND 60.0 #ifndef CGGEOMETRY_LXSUPPORT_H_
CG_INLINE CGPoint
LXS_CGPointAdd(CGPoint point1, CGPoint point2) {
return CGPointMake(point1.x + point2.x, point1.y + point2.y);
}
#endif typedef NS_ENUM(NSInteger, LXScrollingDirection) {
LXScrollingDirectionUnknown = ,
LXScrollingDirectionUp,
LXScrollingDirectionDown,
LXScrollingDirectionLeft,
LXScrollingDirectionRight
}; static NSString * const kLXScrollingDirectionKey = @"LXScrollingDirection";
static NSString * const kLXCollectionViewKeyPath = @"collectionView"; @interface CADisplayLink (LX_userInfo)
@property (nonatomic, copy) NSDictionary *LX_userInfo;
@end @implementation CADisplayLink (LX_userInfo)
- (void) setLX_userInfo:(NSDictionary *) LX_userInfo {
objc_setAssociatedObject(self, "LX_userInfo", LX_userInfo, OBJC_ASSOCIATION_COPY);
} - (NSDictionary *) LX_userInfo {
return objc_getAssociatedObject(self, "LX_userInfo");
}
@end @interface UICollectionViewCell (LXReorderableCollectionViewFlowLayout) - (UIImage *)LX_rasterizedImage; @end @implementation UICollectionViewCell (LXReorderableCollectionViewFlowLayout) - (UIImage *)LX_rasterizedImage {
UIGraphicsBeginImageContextWithOptions(self.bounds.size, self.isOpaque, 0.0f);
[self.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return image;
} @end @interface LXReorderableCollectionViewFlowLayout () @property (strong, nonatomic) NSIndexPath *selectedItemIndexPath;
@property (strong, nonatomic) UIView *currentView;
@property (assign, nonatomic) CGPoint currentViewCenter;
@property (assign, nonatomic) CGPoint panTranslationInCollectionView;
@property (strong, nonatomic) CADisplayLink *displayLink; @property (assign, nonatomic, readonly) id<LXReorderableCollectionViewDataSource> dataSource;
@property (assign, nonatomic, readonly) id<LXReorderableCollectionViewDelegateFlowLayout> delegate; @end @implementation LXReorderableCollectionViewFlowLayout - (void)setDefaults {
_scrollingSpeed = 300.0f;
_scrollingTriggerEdgeInsets = UIEdgeInsetsMake(50.0f, 50.0f, 50.0f, 50.0f);
} - (void)setupCollectionView {
_longPressGestureRecognizer = [[UILongPressGestureRecognizer alloc] initWithTarget:self
action:@selector(handleLongPressGesture:)];
_longPressGestureRecognizer.delegate = self; // Links the default long press gesture recognizer to the custom long press gesture recognizer we are creating now
// by enforcing failure dependency so that they doesn't clash.
for (UIGestureRecognizer *gestureRecognizer in self.collectionView.gestureRecognizers) {
if ([gestureRecognizer isKindOfClass:[UILongPressGestureRecognizer class]]) {
[gestureRecognizer requireGestureRecognizerToFail:_longPressGestureRecognizer];
}
} [self.collectionView addGestureRecognizer:_longPressGestureRecognizer]; _panGestureRecognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self
action:@selector(handlePanGesture:)];
_panGestureRecognizer.delegate = self;
[self.collectionView addGestureRecognizer:_panGestureRecognizer]; // Useful in multiple scenarios: one common scenario being when the Notification Center drawer is pulled down
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(handleApplicationWillResignActive:) name: UIApplicationWillResignActiveNotification object:nil];
} - (id)init {
self = [super init];
if (self) {
[self setDefaults];
[self addObserver:self forKeyPath:kLXCollectionViewKeyPath options:NSKeyValueObservingOptionNew context:nil];
}
return self;
} - (id)initWithCoder:(NSCoder *)aDecoder {
self = [super initWithCoder:aDecoder];
if (self) {
[self setDefaults];
[self addObserver:self forKeyPath:kLXCollectionViewKeyPath options:NSKeyValueObservingOptionNew context:nil];
}
return self;
} - (void)dealloc {
[self invalidatesScrollTimer];
[self removeObserver:self forKeyPath:kLXCollectionViewKeyPath];
[[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationWillResignActiveNotification object:nil];
} - (void)applyLayoutAttributes:(UICollectionViewLayoutAttributes *)layoutAttributes {
if ([layoutAttributes.indexPath isEqual:self.selectedItemIndexPath]) {
layoutAttributes.hidden = YES;
}
} - (id<LXReorderableCollectionViewDataSource>)dataSource {
return (id<LXReorderableCollectionViewDataSource>)self.collectionView.dataSource;
} - (id<LXReorderableCollectionViewDelegateFlowLayout>)delegate {
return (id<LXReorderableCollectionViewDelegateFlowLayout>)self.collectionView.delegate;
} - (void)invalidateLayoutIfNecessary {
NSIndexPath *newIndexPath = [self.collectionView indexPathForItemAtPoint:self.currentView.center];
NSIndexPath *previousIndexPath = self.selectedItemIndexPath; if ((newIndexPath == nil) || [newIndexPath isEqual:previousIndexPath]) {
return;
} if ([self.dataSource respondsToSelector:@selector(collectionView:itemAtIndexPath:canMoveToIndexPath:)] &&
![self.dataSource collectionView:self.collectionView itemAtIndexPath:previousIndexPath canMoveToIndexPath:newIndexPath]) {
return;
} self.selectedItemIndexPath = newIndexPath; if ([self.dataSource respondsToSelector:@selector(collectionView:itemAtIndexPath:willMoveToIndexPath:)]) {
[self.dataSource collectionView:self.collectionView itemAtIndexPath:previousIndexPath willMoveToIndexPath:newIndexPath];
} __weak typeof(self) weakSelf = self;
[self.collectionView performBatchUpdates:^{
__strong typeof(self) strongSelf = weakSelf;
if (strongSelf) {
[strongSelf.collectionView deleteItemsAtIndexPaths:@[ previousIndexPath ]];
[strongSelf.collectionView insertItemsAtIndexPaths:@[ newIndexPath ]];
}
} completion:^(BOOL finished) {
__strong typeof(self) strongSelf = weakSelf;
if ([strongSelf.dataSource respondsToSelector:@selector(collectionView:itemAtIndexPath:didMoveToIndexPath:)]) {
[strongSelf.dataSource collectionView:strongSelf.collectionView itemAtIndexPath:previousIndexPath didMoveToIndexPath:newIndexPath];
}
}];
} - (void)invalidatesScrollTimer {
if (!self.displayLink.paused) {
[self.displayLink invalidate];
}
self.displayLink = nil;
} - (void)setupScrollTimerInDirection:(LXScrollingDirection)direction {
if (!self.displayLink.paused) {
LXScrollingDirection oldDirection = [self.displayLink.LX_userInfo[kLXScrollingDirectionKey] integerValue]; if (direction == oldDirection) {
return;
}
} [self invalidatesScrollTimer]; self.displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(handleScroll:)];
self.displayLink.LX_userInfo = @{ kLXScrollingDirectionKey : @(direction) }; [self.displayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
} #pragma mark - Target/Action methods // Tight loop, allocate memory sparely, even if they are stack allocation.
- (void)handleScroll:(CADisplayLink *)displayLink {
LXScrollingDirection direction = (LXScrollingDirection)[displayLink.LX_userInfo[kLXScrollingDirectionKey] integerValue];
if (direction == LXScrollingDirectionUnknown) {
return;
} CGSize frameSize = self.collectionView.bounds.size;
CGSize contentSize = self.collectionView.contentSize;
CGPoint contentOffset = self.collectionView.contentOffset;
UIEdgeInsets contentInset = self.collectionView.contentInset;
// Important to have an integer `distance` as the `contentOffset` property automatically gets rounded
// and it would diverge from the view's center resulting in a "cell is slipping away under finger"-bug.
CGFloat distance = rint(self.scrollingSpeed / LX_FRAMES_PER_SECOND);
CGPoint translation = CGPointZero; switch(direction) {
case LXScrollingDirectionUp: {
distance = -distance;
CGFloat minY = 0.0f - contentInset.top; if ((contentOffset.y + distance) <= minY) {
distance = -contentOffset.y - contentInset.top;
} translation = CGPointMake(0.0f, distance);
} break;
case LXScrollingDirectionDown: {
CGFloat maxY = MAX(contentSize.height, frameSize.height) - frameSize.height + contentInset.bottom; if ((contentOffset.y + distance) >= maxY) {
distance = maxY - contentOffset.y;
} translation = CGPointMake(0.0f, distance);
} break;
case LXScrollingDirectionLeft: {
distance = -distance;
CGFloat minX = 0.0f - contentInset.left; if ((contentOffset.x + distance) <= minX) {
distance = -contentOffset.x - contentInset.left;
} translation = CGPointMake(distance, 0.0f);
} break;
case LXScrollingDirectionRight: {
CGFloat maxX = MAX(contentSize.width, frameSize.width) - frameSize.width + contentInset.right; if ((contentOffset.x + distance) >= maxX) {
distance = maxX - contentOffset.x;
} translation = CGPointMake(distance, 0.0f);
} break;
default: {
// Do nothing...
} break;
} self.currentViewCenter = LXS_CGPointAdd(self.currentViewCenter, translation);
self.currentView.center = LXS_CGPointAdd(self.currentViewCenter, self.panTranslationInCollectionView);
self.collectionView.contentOffset = LXS_CGPointAdd(contentOffset, translation);
} - (void)handleLongPressGesture:(UILongPressGestureRecognizer *)gestureRecognizer {
switch(gestureRecognizer.state) {
case UIGestureRecognizerStateBegan: {
NSIndexPath *currentIndexPath = [self.collectionView indexPathForItemAtPoint:[gestureRecognizer locationInView:self.collectionView]]; if ([self.dataSource respondsToSelector:@selector(collectionView:canMoveItemAtIndexPath:)] &&
![self.dataSource collectionView:self.collectionView canMoveItemAtIndexPath:currentIndexPath]) {
return;
} self.selectedItemIndexPath = currentIndexPath; if ([self.delegate respondsToSelector:@selector(collectionView:layout:willBeginDraggingItemAtIndexPath:)]) {
[self.delegate collectionView:self.collectionView layout:self willBeginDraggingItemAtIndexPath:self.selectedItemIndexPath];
} UICollectionViewCell *collectionViewCell = [self.collectionView cellForItemAtIndexPath:self.selectedItemIndexPath]; self.currentView = [[UIView alloc] initWithFrame:collectionViewCell.frame]; collectionViewCell.highlighted = YES;
UIImageView *highlightedImageView = [[UIImageView alloc] initWithImage:[collectionViewCell LX_rasterizedImage]];
highlightedImageView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
highlightedImageView.alpha = 1.0f; collectionViewCell.highlighted = NO;
UIImageView *imageView = [[UIImageView alloc] initWithImage:[collectionViewCell LX_rasterizedImage]];
imageView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
imageView.alpha = 0.0f; [self.currentView addSubview:imageView];
[self.currentView addSubview:highlightedImageView];
[self.collectionView addSubview:self.currentView]; self.currentViewCenter = self.currentView.center; __weak typeof(self) weakSelf = self;
[UIView
animateWithDuration:0.3
delay:0.0
options:UIViewAnimationOptionBeginFromCurrentState
animations:^{
__strong typeof(self) strongSelf = weakSelf;
if (strongSelf) {
strongSelf.currentView.transform = CGAffineTransformMakeScale(1.1f, 1.1f);
highlightedImageView.alpha = 0.0f;
imageView.alpha = 1.0f;
}
}
completion:^(BOOL finished) {
__strong typeof(self) strongSelf = weakSelf;
if (strongSelf) {
[highlightedImageView removeFromSuperview]; if ([strongSelf.delegate respondsToSelector:@selector(collectionView:layout:didBeginDraggingItemAtIndexPath:)]) {
[strongSelf.delegate collectionView:strongSelf.collectionView layout:strongSelf didBeginDraggingItemAtIndexPath:strongSelf.selectedItemIndexPath];
}
}
}]; [self invalidateLayout];
} break;
case UIGestureRecognizerStateCancelled:
case UIGestureRecognizerStateEnded: {
NSIndexPath *currentIndexPath = self.selectedItemIndexPath; if (currentIndexPath) {
if ([self.delegate respondsToSelector:@selector(collectionView:layout:willEndDraggingItemAtIndexPath:)]) {
[self.delegate collectionView:self.collectionView layout:self willEndDraggingItemAtIndexPath:currentIndexPath];
} self.selectedItemIndexPath = nil;
self.currentViewCenter = CGPointZero; UICollectionViewLayoutAttributes *layoutAttributes = [self layoutAttributesForItemAtIndexPath:currentIndexPath]; __weak typeof(self) weakSelf = self;
[UIView
animateWithDuration:0.3
delay:0.0
options:UIViewAnimationOptionBeginFromCurrentState
animations:^{
__strong typeof(self) strongSelf = weakSelf;
if (strongSelf) {
strongSelf.currentView.transform = CGAffineTransformMakeScale(1.0f, 1.0f);
strongSelf.currentView.center = layoutAttributes.center;
}
}
completion:^(BOOL finished) {
__strong typeof(self) strongSelf = weakSelf;
if (strongSelf) {
[strongSelf.currentView removeFromSuperview];
strongSelf.currentView = nil;
[strongSelf invalidateLayout]; if ([strongSelf.delegate respondsToSelector:@selector(collectionView:layout:didEndDraggingItemAtIndexPath:)]) {
[strongSelf.delegate collectionView:strongSelf.collectionView layout:strongSelf didEndDraggingItemAtIndexPath:currentIndexPath];
}
}
}];
}
} break; default: break;
}
} - (void)handlePanGesture:(UIPanGestureRecognizer *)gestureRecognizer {
switch (gestureRecognizer.state) {
case UIGestureRecognizerStateBegan:
case UIGestureRecognizerStateChanged: {
self.panTranslationInCollectionView = [gestureRecognizer translationInView:self.collectionView];
CGPoint viewCenter = self.currentView.center = LXS_CGPointAdd(self.currentViewCenter, self.panTranslationInCollectionView); [self invalidateLayoutIfNecessary]; switch (self.scrollDirection) {
case UICollectionViewScrollDirectionVertical: {
if (viewCenter.y < (CGRectGetMinY(self.collectionView.bounds) + self.scrollingTriggerEdgeInsets.top)) {
[self setupScrollTimerInDirection:LXScrollingDirectionUp];
} else {
if (viewCenter.y > (CGRectGetMaxY(self.collectionView.bounds) - self.scrollingTriggerEdgeInsets.bottom)) {
[self setupScrollTimerInDirection:LXScrollingDirectionDown];
} else {
[self invalidatesScrollTimer];
}
}
} break;
case UICollectionViewScrollDirectionHorizontal: {
if (viewCenter.x < (CGRectGetMinX(self.collectionView.bounds) + self.scrollingTriggerEdgeInsets.left)) {
[self setupScrollTimerInDirection:LXScrollingDirectionLeft];
} else {
if (viewCenter.x > (CGRectGetMaxX(self.collectionView.bounds) - self.scrollingTriggerEdgeInsets.right)) {
[self setupScrollTimerInDirection:LXScrollingDirectionRight];
} else {
[self invalidatesScrollTimer];
}
}
} break;
}
} break;
case UIGestureRecognizerStateCancelled:
case UIGestureRecognizerStateEnded: {
[self invalidatesScrollTimer];
} break;
default: {
// Do nothing...
} break;
}
} #pragma mark - UICollectionViewLayout overridden methods - (NSArray *)layoutAttributesForElementsInRect:(CGRect)rect {
NSArray *layoutAttributesForElementsInRect = [super layoutAttributesForElementsInRect:rect]; for (UICollectionViewLayoutAttributes *layoutAttributes in layoutAttributesForElementsInRect) {
switch (layoutAttributes.representedElementCategory) {
case UICollectionElementCategoryCell: {
[self applyLayoutAttributes:layoutAttributes];
} break;
default: {
// Do nothing...
} break;
}
} return layoutAttributesForElementsInRect;
} - (UICollectionViewLayoutAttributes *)layoutAttributesForItemAtIndexPath:(NSIndexPath *)indexPath {
UICollectionViewLayoutAttributes *layoutAttributes = [super layoutAttributesForItemAtIndexPath:indexPath]; switch (layoutAttributes.representedElementCategory) {
case UICollectionElementCategoryCell: {
[self applyLayoutAttributes:layoutAttributes];
} break;
default: {
// Do nothing...
} break;
} return layoutAttributes;
} #pragma mark - UIGestureRecognizerDelegate methods - (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer {
if ([self.panGestureRecognizer isEqual:gestureRecognizer]) {
return (self.selectedItemIndexPath != nil);
}
return YES;
} - (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer {
if ([self.longPressGestureRecognizer isEqual:gestureRecognizer]) {
return [self.panGestureRecognizer isEqual:otherGestureRecognizer];
} if ([self.panGestureRecognizer isEqual:gestureRecognizer]) {
return [self.longPressGestureRecognizer isEqual:otherGestureRecognizer];
} return NO;
} #pragma mark - Key-Value Observing methods - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context {
if ([keyPath isEqualToString:kLXCollectionViewKeyPath]) {
if (self.collectionView != nil) {
[self setupCollectionView];
} else {
[self invalidatesScrollTimer];
}
}
} #pragma mark - Notifications - (void)handleApplicationWillResignActive:(NSNotification *)notification {
self.panGestureRecognizer.enabled = NO;
self.panGestureRecognizer.enabled = YES;
} #pragma mark - Depreciated methods #pragma mark Starting from 0.1.0
- (void)setUpGestureRecognizersOnCollectionView {
// Do nothing...
} @end

LXReorderableCollectionViewFlowLayout.m

效果

    

【推荐】iOS集合视图的可重新排序的layout的更多相关文章

  1. iOS集合视图单元格高亮和选中的区别

    大熊猫猪·侯佩原创或翻译作品.欢迎转载,转载请注明出处. 如果觉得写的不好请多提意见,如果觉得不错请多多支持点赞.谢谢! hopy ;) 免责申明:本博客提供的所有翻译文章原稿均来自互联网,仅供学习交 ...

  2. 集合视图控制器(CollectionViewController) 、 标签控制器(TabBarController) 、 高级控件介绍

    1 创建集合视图,设置相关属性以满足要求 1.1 问题 集合视图控制器UIConllectionViewController是一个展示大量数据的控制器,系统默认管理着一个集合视图UICollectio ...

  3. iOS:集合视图UICollectionView、集合视图控制器UICollectionViewController、集合视图单元格UICollectionViewCell(创建表格的另一种控件)

    两种创建表格方式的比较:表格视图.集合视图(二者十分类似) <1>相同点:   表格视图:UITableView(位于storyboard中,通过UIViewController控制器实现 ...

  4. 集合视图UICollectionView 介绍及其示例程序

    UICollectionView是一种新的数据展示方式,简单来说可以把它理解成多列的UITableView.如果你用过iBooks的话,可 能你还对书架布局有一定印象,一个虚拟书架上放着你下载和购买的 ...

  5. UICollectionView(集合视图)以及自定义集合视图

    一.UICollectionView集合视图           其继承自UIScrollView.         UICollectionView类是iOS6新引进的API,用于展示集合视图,布局 ...

  6. UICollectionView集合视图的概念

    如何创建UICollectionView 集合视图的布局UICollectionViewFlowLayout 自定义cell 布局协议UICollectionViewDelegateFlowLayou ...

  7. swift:创建集合视图UICollectionView

    swift中创建集合视图和OC中差不多,主要是实现UICollectionViewDataSource数据源协议和UICollectionViewDelegateFlowLayout自定义布局协议,其 ...

  8. UICollectionView 集合视图用法,自定义Cell

    在View里面 //1.创建UICollectionViewFlowLayout UICollectionViewFlowLayout *flowLayout=[[UICollectionViewFl ...

  9. iOS 让视图UIView单独显示某一侧的边框线

    iOS 让视图UIView 单独显示某一侧的边框线   有时候需要让view显示某一侧的边框线,这时设置layer的border是达不到效果的.在网上查阅资料发现有一个投机取巧的办法,原理是给view ...

随机推荐

  1. HBase、Redis、MongoDB、Couchbase、LevelDB主流 NoSQL 数据库的对比

    最近小组准备启动一个 node 开源项目,从前端亲和力.大数据下的IO性能.可扩展性几点入手挑选了 NoSql 数据库,但具体使用哪一款产品还需要做一次选型. 我们最终把选项范围缩窄在 HBase.R ...

  2. [LeetCode] Range Sum Query - Immutable & Range Sum Query 2D - Immutable

    Range Sum Query - Immutable Given an integer array nums, find the sum of the elements between indice ...

  3. Zone.js 简介 & 抛砖引玉

    Zone.js是angular团队参照NodeJS的Domain,Dart的Zone,为angular 2开发的核心组件. 一开始,我对Zone.js是拒绝的.我们知道类似的 Domain 模块,主要 ...

  4. 读匿名object对象的属性值

    读匿名object对象的属性值 1.定义读object对象值的功能方法 public static class StaticClass { public static string ValueByKe ...

  5. 生活科技两相宜:(一)Win7使用微软SkyDrive网盘简易教程

    今天得写一个Win7使用微软SkyDrive网盘的简易教程,主要是给我老婆看,顺便贴出来给大家共享一下:)    使用微软SkyDrive网盘有两个层次.一个是使用网页版,这个跟使用163或者QQ网盘 ...

  6. 自定义android RadioButton View,添加较为灵活的布局处理方式

    android的RadioButton的使用历来都让人比较头疼,如在布局方面,图案.文字无法分别设置padding等,另外,低版本的android RadioGroup不支持换行排列的RadioBut ...

  7. 修改windows系統下xampp中apache端口被其他程式占用的問題

    windows 7安裝後啟動xampp, 提示port 443 被其他程式占用. 網上查找解決方案: http://stackoverflow.com/questions/21182512/how-t ...

  8. chm格式文件能打开,但看不到内容问题

    是chm格式的能打开文件,也能看到左边的目录信息,但是无法显示右面的具体内容.报错:无法显示网页.错误页面的url是:res://C:WINDOWSsystem32shdoclc.dll/dnserr ...

  9. asp.net MVC 自动下载apk

    在Asp.net MVC中直接把.apk文件放入/Upload/App/ 路径下,然后通过IIS发布完之后,再通过http://xxx/Upload/App/xx.apk访问是访问不到的,因此不能下载 ...

  10. EETOP中关于Gm仿真的一些帖子的总结

    1. cadence画gm曲线 电路里,要把漏的电源dc值设置成变量,比如叫vds,计算器,info标签,点op,然后点管子,在op窗口点list,选gm,然后把这个公式弄到ADE的outputs那里 ...