### It’s June, I feel degraded for a month, haha. Today I will update another article, the main content, about the packaging of a multi-level selection framework and several strange pits encountered in the project. ##### multi-level selection framework implementation of the framework effect picture is as follows:

Multilevel filter code GSMultipleChoiceView address

  • Main functions: to realize there are multiple options on the left, can be adaptive rolling and set the font at the bottom of the width and the underline the width of the screening of multiple choice, can remember the last time the effect of selected, click on the primary filter, secondary filter closed and refresh data, can according to the different level of click on the title shows different secondary title screen name. The level 1 headings to the left of the filter can be more than 4 and will scroll automatically.
  • The loading method for calling method level 1 filtering is as follows
 MultipleChoiceView =[[RedChipMultipleChoiceView alloc]initWithFrame:CGRectMake(0, 64, SCREEN_WIDTH, 45*ratio_width) titles:@[@"To be extended"The @"Not due"The @"It's over"The @"All"] moreSelctBtnTitle:@"Screening" btn_w:SCREEN_WIDTH/5];
Copy the code

The agent following MultipleChoiceView creates a display of secondary headings based on click filtering for easy customization

#pragma mark - Header controlled proxy method-(void)redChipClicktWith:(NSNumber *)nowSelect{NSLog(@)"-----%ld",[nowSelect integerValue]);
    //    [MultipleChoiceView.moreSelectBtn setTitleColor:[Toolkit getColor:hex_606060] forState:UIControlStateNormal];
    [MultipleChoiceView.moreSelectBtn setTitleColor:[UIColor blackColor] forState:UIControlStateNormal];
    
    MultipleChoiceView.selcetBtnIsSelect = NO;
    MultipleChoiceView.rightView.image =[UIImage imageNamed:@"Red chip optimized new icon triangle - next -@2x"]; self.SlectbottomView.hidden =YES; currentSelctNum = nowSelect; GoodList_sort = @ by default"1";
    goodsList_order = @"desc"; // Here, according to the returned data after clicking, do network request, interface refresh and other operations}Copy the code

Click the Filter button to create secondary title processing logic

// Click the filter button -(void)clickMoreSelcetBtn{if ([currentSelctNum integerValue] == 4) {
        arrName = @[@"Participation Time"The @"End time"The @"Reward"];
    }else{
        arrName = @[@"Participation Time"The @"Due Time"The @"Reward"];
    }
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.05 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        [self prepareMenuViewSubviews];
        
    });
    
    if (MultipleChoiceView.selcetBtnIsSelect) {
        //        [MultipleChoiceView.moreSelectBtn setTitleColor:[Toolkit getColor:hex_606060] forState:UIControlStateNormal];
        [MultipleChoiceView.moreSelectBtn setTitleColor:[UIColor blackColor] forState:UIControlStateNormal];
        
        MultipleChoiceView.selcetBtnIsSelect = NO;
        MultipleChoiceView.rightView.image =[UIImage imageNamed:@"Red chip optimized new icon triangle - next -@2x"];
        self.SlectbottomView.hidden =YES;
    }else{
        //        [MultipleChoiceView.moreSelectBtn setTitleColor:[Toolkit getColor:hex_ff5600] forState:UIControlStateNormal];
        [MultipleChoiceView.moreSelectBtn setTitleColor:[UIColor redColor] forState:UIControlStateNormal];
        
        MultipleChoiceView.selcetBtnIsSelect = YES;
        MultipleChoiceView.rightView.image =[UIImage imageNamed:@"Red chip optimized new icon triangle - up @2x"]; self.SlectbottomView.hidden =NO; }}Copy the code

Gif02.gif #### project pit happy time is always short next, talk about the pit encountered in the recent project, recently responsible for the module more, the change of the old code can be described as a pit step by step ah, the following from the degree of depression a little bit about it.

00

Caught off guard by the pit of iOS10.3

Mall for goods in the preferential price processing of the line failure. Reason: After the 10.3 update (at least this is what I found), underlined rich text processing with Chinese prices or symbols doesn’t work anymore. The previous handling code is as follows:

 NSDictionary *attribtDic = @{NSStrikethroughStyleAttributeName: [NSNumber numberWithInteger:NSUnderlineStyleSingle]};
    NSMutableAttributedString *attribtStr_origin = [[NSMutableAttributedString alloc]initWithString:[NSString stringWithFormat:@"Price :¥%@",[goods_info objectForKey:@"market_price"]] attributes:attribtDic];
    self.current_price_lbl.attributedText=attribtStr_origin;
Copy the code

The new solution is as follows:

    NSUInteger length = [[NSString stringWithFormat:@"Price :¥%@",[goods_info objectForKey:@"market_price"]] length];
    NSMutableAttributedString *attri = [[NSMutableAttributedString alloc] initWithString:[NSString stringWithFormat:@"Price :¥%@",[goods_info objectForKey:@"market_price"]]];
    [attri setAttributes:@{NSStrikethroughStyleAttributeName: [NSNumber numberWithInteger:NSUnderlineStyleSingle], NSBaselineOffsetAttributeName : @(NSUnderlineStyleSingle),NSForegroundColorAttributeName:[UIColor lightGrayColor]} range:NSMakeRange(3,length-3)];
    [self.current_price_lbl setAttributedText:attri];
		
Copy the code

Add a rich text attribute:

NSBaselineOffsetAttributeName : @(NSUnderlineStyleSingle)
Copy the code

Now that we’re done here, we’re going to display rich text paragraphs in two common rich text processing ways:

 NSAttributedString * attrStr = [[NSAttributedString alloc] initWithData:[shareTexe dataUsingEncoding:NSUnicodeStringEncoding] options:@{ NSDocumentTypeDocumentAttribute: NSHTMLTextDocumentType} documentAttributes:nil error:nil];
 [self.midDesclabel setAttributedText:attrStr];
 [self.midDesclabel sizeToFit];
Copy the code

Do rich text processing for part of the text

cell.voucher_RedChipCountLabel.textColor = [Toolkit getColor:hex_606060];
NSMutableAttributedString* attribute=[[NSMutableAttributedString alloc] initWithString:indexRow_RedChipCountStr];
[attribute addAttribute:NSForegroundColorAttributeName value:[Toolkit getColor:hex_ff5600] range:NSMakeRange(5, indexRow_RedChipCountStr.length - 5)];
[attribute addAttribute:NSFontAttributeName value:[UIFont systemFontOfSize:14] range:NSMakeRange(0, 5)];
[attribute addAttribute:NSFontAttributeName value:[UIFont systemFontOfSize:16] range:NSMakeRange(5, indexRow_RedChipCountStr.length - 5)];
cell.voucher_RedChipCountLabel.attributedText = attribute;

Copy the code

###### zxing-object TWO-DIMENSIONAL code shows the pit below the start of the test did not encounter, but the user feedback of the pit

01

  • Scene, generate a picture with two-dimensional code, two ways of processing, one is to save to local recognition, one is to share directly to QQ.
  • Problem: Some users can not recognize the TWO-DIMENSIONAL code, the generated pictures saved to the local direct recognition can be recognized, directly shared to QQ, part of the pictures can not be recognized. The method of generating two-dimensional code is as follows:
    dispatch_async(dispatch_get_main_queue(), ^{
            
            if(str ! = nil) { ZXMultiFormatWriter *writer = [[ZXMultiFormatWriter alloc] init]; ZXEncodeHints *hints = [ZXEncodeHints hints]; hints.encoding = NSUTF8StringEncoding; hints.dataMatrixShape =ZXDataMatrixSymbolShapeHintForceSquare; hints.margin = [NSNumber numberWithInt:0.]; hints.errorCorrectionLevel = [ZXQRCodeErrorCorrectionLevel errorCorrectionLevelH]; NSString *qrString = str; ZXBitMatrix *result = [writer encode:qrString format:kBarcodeFormatQRCode width:500 height:500 hints:hints error:nil];if(result) { CGImageRef image = [[ZXImage imageWithMatrix:result] cgimage]; UIImage *image1 = [UIImage imageWithCGImage:image]; / / qr code original self. ShareErWeiMaView. Image = image1; }else{ self.shareErWeiMaView.image = nil; }}});Copy the code

Due to the generation of two-dimensional code fault tolerance level and range have been set, and there is no LOGO block, the focus is to save to local recognition, so it is strange, the final solution increases the range.

  ZXBitMatrix *result = [writer encode:qrString format:kBarcodeFormatQRCode width:500 height:500 hints:hints error:nil];
Copy the code

The scope of the above sentence code has been increased to solve the problem that part of the TWO-DIMENSIONAL code can not be recognized.

##### unsolved mystery of god pit, heart plug has not been able to reappear, so say more.

  • Bug source: User feedback
  • Cause: In the multi-stage screening, the display is chaotic, the first click is chaotic, refresh the normal, the specific interface is, the screen has ended the display of the interface.

The normally displayed ended page is shown as follows:

PNG normal unfinished data containing the countdown is shown as follows:

PNG User feedback bug, screen shot as follows:

Feedback. PNG

As can be seen from the figure, the countdown is displayed at the end, for a Tableview, the first time is the reuse of the problem, or the control of the show hide judgment logic out of the problem. In the old code, respectively, timeLabel and endTimeLabel are used to display the ended title and countdown title respectively, and a field in the background is used to control the display content of the title. TimeLabel and endTimeLabel are displayed and hidden according to the background data returned by different cells. The layout of the two controls is as follows:

[self.cell_iconImageView_1 makeConstraints:^(MASConstraintMaker* make){ make.top.equalTo(self.contentView).offset(15*ratio_width);  make.bottom.equalTo(self.contentView).offset(-15*ratio_width);  make.left.equalTo(self.contentView).offset(10*ratio_width); make.width.equalTo(self.cell_ImageView_1.height); }]; [self.timeLabel makeConstraints:^(MASConstraintMaker* make){ make.top.equalTo(self.addRewardMoney.mas_bottom).offset(5*ratio_width);  make.left.equalTo(self.cell_iconImageView_1.right).offset(10*ratio_width); make.right.equalTo(self.contentView);  make.height.equalTo(19*ratio_width); }]; [self.endTimeLabel makeConstraints:^(MASConstraintMaker* make){ make.bottom.equalTo(self.contentView).offset(-10*ratio_width);  make.left.equalTo(self.cell_iconImageView_1.right).offset(10*ratio_width); make.right.equalTo(self.contentView);  make.height.equalTo(25*ratio_width); }];Copy the code

The two controls are arranged from the left according to the image, and there is some crossover. We deliberately make them both appear as follows:

Assuming the error graph.png, you can see that even if the hidden error is shown, it should appear as shown above and should not appear as shown in the feedback graph below

Feedback graph marks therefore

  • Doubt 1: There is no control so far, how can it be displayed?
  • Doubt 2: the display content of the control is judged in each cell.
    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{}

              NSInteger status = [[NSString stringWithFormat:@"% @",[[_dataArray_ing objectAtIndex:indexPath.section] objectForKey:@"ostatus"]] integerValue];
                if (status == 2) {
                    
                    cell.timeLabel.text=@"It's over";
                    
                }else{
                 
                    if (seconds==0) {
                        if ([[[_dataArray_ing objectAtIndex:indexPath.section] objectForKey:@"activity"] intValue]==10) {
                            cell.timeLabel.text=@"Expired";
                        }
                        else
                        {
                            cell.timeLabel.text=@"To be extended"; }}else{
                        if ([_dataArray_ing count]>[totalLastTime count]&&[totalLastTime count]<(indexPath.section+1)) {
                            NSDictionary *dic = @{@"indexPath":[NSString stringWithFormat:@"%ld",indexPath.section],@"lastTime": [[_dataArray_ing objectAtIndex:indexPath.section] objectForKey:@"remain_time" ]};
                            [totalLastTime addObject:dic];
                            cell.timeLabel.text= [NSString stringWithFormat:@"Remaining time :%@",[Toolkit formatSecondToData:seconds]]; }}}Copy the code
  • Question 3: During the development process, this situation never occurred in multiple test accounts and the three-day test cycle. After the feedback, several people still failed to test for several times.
  • Confusion 4 According to feedback, the first click is such a pull up refresh recovery is more strange, because each click on a new level menu is equivalent to a new refresh.

Unfortunately, there is no feedback on the user’s account information, and only one feedback, otherwise the problem is not pulling the background in the end.