global with sharing class PersonalEvaluationClipEditController {
    public List<ClipInfo> clipList { get; set; }
    public String sid { get; private set; }
    public String newOrder { get; set; }
    public Integer delLineNo { get; set; }
    
    private SMARM__c defaultSmarm;
    private Map<String, Schema.SObjectField> fieldMap;
    private List<Attachment> attList;
    
    public PersonalEvaluationClipEditController() {
        delLineNo = 0;
        defaultSmarm = new SMARM__c();
        
        Schema.DescribeSobjectResult s = SMARM__c.sObjectType.getDescribe();
        fieldMap = s.fields.getMap();
        attList = new List<Attachment>();
    }
    
    @RemoteAction
    global static Map<String, Object> getAttachmentBody(String sid) {
        List<Attachment> attList = ControllerUtil.getSmarmAtts(sid);
        Map<String, Object> attMap = new Map<String, Object>();
        Integer i = 1;
        for (Attachment att : attList) {
            Map<String, Object> tmpMap = new Map<String, Object>();
            tmpMap.put('Id', att.Id);
            tmpMap.put('Name', att.Name);
            tmpMap.put('Body', EncodingUtil.Base64Encode(att.Body));
            
            attMap.put(String.valueOf(i), tmpMap);
            i++;
        }
        attMap.put('AttCnt', attList.size());
        return attMap;
    }
    
    public void init() {
        clipList = new List<ClipInfo>();
        
        sid = System.currentPageReference().getParameters().get('id');
        // SMARMを検索
        String sql = 'select ';
        String fields = '';
        for (String field : fieldMap.keySet()) {
            if (fields.length() > 0) {
                fields += ', '; 
            }
            fields += field;
        }
        sql += fields;
        sql += ' from SMARM__c where Id = \'' + sid + '\'';
        List<SMARM__c> sList = ControllerUtil.getSmarmById(sql);
        
        if (sList.size() > 0) {
            defaultSmarm = sList[0];
            Map<String, Attachment> attMap = new Map<String, Attachment>();
            for (Attachment att : ControllerUtil.getSmarmAtts(sid)) {
                attMap.put(att.Name, att);
            }
            //attList = attMap.values();
            newOrder = '';
            
            Integer idx = 1;
            for (Integer i = 1; i <= Integer.valueOf(System.Label.SmarmClipNum); i++) {
                String reportNameApi = 'ReportName' + i + '__c';
                String imgApi = 'Image' + i + '__c';
                String commentApi = 'Comment' + i + '__c';
                // ReportNameで判断、ReportNameあり、画像なしのケースを無視
                if (fieldMap.get(reportNameApi) != null && defaultSmarm.get(reportNameApi) != null) {
                    clipList.add(new ClipInfo(String.valueOf(defaultSmarm.get(reportNameApi)), String.valueOf(defaultSmarm.get(imgApi)), String.valueOf(defaultSmarm.get(commentApi))));
                    clipList[clipList.size() - 1].lineNo = idx;
                    clipList[clipList.size() - 1].idx = i;
                    if (attMap.containsKey(i + '.' + defaultSmarm.get(reportNameApi))) {
                        clipList[clipList.size() - 1].attId = attMap.get(i + '.' + defaultSmarm.get(reportNameApi)).Id;
                    }
                    
                    // 順番Strをセット
                    newOrder += idx + ',';
                    idx++;
                }
            }
            if (String.isBlank(newOrder) == false) newOrder = newOrder.substring(0, newOrder.length() - 1);
        } else {
            // add error
            ApexPages.addmessage(new ApexPages.message(ApexPages.severity.INFO, '无法取得数据'));
            return;
        }
    }
    
    // 削除ボタン
    public PageReference deleteClip() {
        Savepoint sp = Database.setSavepoint();
        try {
            SMARM__c smarm = this.changeOrder();
            ControllerUtil.upsertSMARM(smarm);
            
            PageReference pageRef = new PageReference('/apex/PersonalEvaluationClipEdit?id=' + defaultSmarm.Id);
            pageRef.setRedirect(true);
            return pageRef;
        } catch (Exception e) {
            Database.rollback(sp);
            ApexPages.addMessages(e);
            return null;
        }
    }
    
    // ソート保存ボタン
    public PageReference saveOrder() {
        Savepoint sp = Database.setSavepoint();
        try {
            SMARM__c smarm = this.changeOrder();
            ControllerUtil.upsertSMARM(smarm);
            
            PageReference pageRef = new PageReference('/apex/PersonalEvaluationClipEdit?id=' + defaultSmarm.Id);
            pageRef.setRedirect(true);
            return pageRef;
        } catch (Exception e) {
            Database.rollback(sp);
            ApexPages.addMessages(e);
            return null;
        }
    }
    
    // 確定ボタン
    public PageReference complete() {
        Savepoint sp = Database.setSavepoint();
        try {
            SMARM__c smarm = this.changeOrder();
            smarm.OwnerId = defaultSmarm.Review_Target__c;
            smarm.Status__c = '草案中';
            
            // 共有設定用のユーザ配列
            Set<Id> userOrGroupIdList = new Set<Id>();
            // 评价者を入れる
            userOrGroupIdList.add(defaultSmarm.Review_Practitioner__c);
            
            // 部长经理总监
            User target = [SELECT Id, Name, SalesManager__c, BuchangApprovalManagerSales__c, JingliApprovalManager__c, BuchangApprovalManager__c, ZongjianApprovalManager__c FROM User WHERE Id = :defaultSmarm.Review_Practitioner__c];
            smarm.SalesManager__c = target.SalesManager__c == null ? target.Id : target.SalesManager__c;
            smarm.BuchangApprovalManagerSales__c = target.BuchangApprovalManagerSales__c == null ? target.Id : target.BuchangApprovalManagerSales__c;
            smarm.JingliApprovalManager__c = target.JingliApprovalManager__c == null ? target.Id : target.JingliApprovalManager__c;
            smarm.BuchangApprovalManager__c = target.BuchangApprovalManager__c == null ? target.Id : target.BuchangApprovalManager__c;
            smarm.ZongjianApprovalManager__c = target.ZongjianApprovalManager__c == null ? target.Id : target.ZongjianApprovalManager__c;
            userOrGroupIdList.add(smarm.SalesManager__c);
            userOrGroupIdList.add(smarm.BuchangApprovalManagerSales__c);
            userOrGroupIdList.add(smarm.JingliApprovalManager__c);
            userOrGroupIdList.add(smarm.BuchangApprovalManager__c);
            userOrGroupIdList.add(smarm.ZongjianApprovalManager__c);
            
            ControllerUtil.upsertSMARM(smarm);
            
            // 共有設定
            List<String> userAccess  = new List<String>();
            for (Id userOrGroupId : userOrGroupIdList) {
                userAccess.add(userOrGroupId + '_Edit');
            }
            ControllerUtil.setSObjectShare('SMARM__Share', 'SMARMReviewPractitionerShare__c', smarm.Id, userAccess, smarm.OwnerId);
            /*
            List<SMARM__Share> shareObject = new List<SMARM__Share>();
            for (Id userOrGroupId : userOrGroupIdList) {
                SMARM__Share smarmShare = new SMARM__Share(
                    RowCause = 'SMARMReviewPractitionerShare__c',
                    ParentId = smarm.Id,
                    UserOrGroupId = userOrGroupId,
                    AccessLevel = 'Edit'
                );
                shareObject.add(smarmShare);
            }
            ControllerUtil.insertSMARMShare(shareObject);
            */
            PageReference pageRef = new PageReference('/' + defaultSmarm.Id);
            pageRef.setRedirect(true);
            return pageRef;
        } catch (Exception e) {
            Database.rollback(sp);
            ApexPages.addMessages(e);
            return null;
        }
    }
    
    private SMARM__c changeOrder() {
        SMARM__c smarm = new SMARM__c(Id = defaultSmarm.Id);
        
        // 項目内容を全部クリア
        for (Integer i = 1; i <= Integer.valueOf(System.Label.SmarmClipNum); i++) {
            String reportNameApi = 'ReportName' + i + '__c';
            String imgApi = 'Image' + i + '__c';
            String commentApi = 'Comment' + i + '__c';
            if (fieldMap.get(reportNameApi) != null) {
                smarm.put(reportNameApi, null);
                smarm.put(imgApi, null);
                smarm.put(commentApi, null);
            }
        }
        
        // 順番Strのサイズは必ずclipListのサイズと同じ
        List<String> orderList = newOrder.split(',', -1);
        Integer idx = 1;
        List<Attachment> attList = new List<Attachment>();
        for (Integer i = 0; i < orderList.size(); i++) {
            Integer realIdx = Integer.valueOf(orderList[i]);
//system.debug('realIdx = ' + realIdx);
//system.debug('delLineNo = ' + delLineNo);
            // 削除の行を見つけたら
            if (realIdx == delLineNo) {
                // Attachment削除
                String attId = clipList[realIdx - 1].attId;
                ControllerUtil.deleteAttachments(new Attachment[]{new Attachment(Id = attId)});
            } else {
                // readIdx＝LineNo、1から加算なので、clipListからデータを取得する時、-1にする
                String reportName = clipList[realIdx - 1].reportName;
                String img = '<img src=\"' + clipList[realIdx - 1].imgSrc + '\"></img>';
                String attId = clipList[realIdx - 1].attId;
                String comment = clipList[realIdx - 1].comment;
                
                smarm.put('ReportName' + idx + '__c', reportName);
                smarm.put('Image' + idx + '__c', img);
                smarm.put('Comment' + idx + '__c', comment);
                
                // TODO テストクラスの対応
                if (!Test.isRunningTest()) {
                    // Attachment更新
                    attList.add(new Attachment(
                        Id = attId,
                        Name = idx + '.' + reportName
                    ));
                }
                
                idx++;
            }
        }
        ControllerUtil.updateAttachments(attList);
        return smarm;
    }
    
    class ClipInfo {
        public String reportName { get; private set; }
        public String imgSrc { get; private set; }
        public String comment { get; set; }
        public Integer lineNo { get; set; }
        public Integer idx { get; set; }
        public String attId { get; set; }
        
        public ClipInfo(String reportName, String img, String comment) {
            this.reportName = reportName;
            // srcを取得
            String phtTxt = '';
            if (String.isBlank(img) == false) {
                Integer pStt = img.indexOf('<img');
                if (pStt >= 0) {
                    pStt = img.indexOf('src="');
                    if (pStt >= 0) {
                        Integer pEnd = img.indexOf('"', pStt + 5);
                        if (pEnd >= 0) {
                            phtTxt = img.substring(pStt + 5, pEnd);
                            phtTxt = phtTxt.unescapeHtml4();
                        }
                    }
                }
            }
            this.imgSrc = phtTxt;
            
            this.comment = comment;
        }
    }
}