사용자:BANIP/낙서장: 두 판 사이의 차이

리버티게임, 모두가 만들어가는 자유로운 게임
잔글편집 요약 없음
태그: 되돌려진 기여
잔글편집 요약 없음
태그: 되돌려진 기여 시각 편집: 전환됨
1번째 줄: 1번째 줄:
// 프리로딩 가능한 링크 최고 갯수
var previewLimit = 5
var previewLimit = 5
var getParsedDocumentPromise = (function(link){
    var mwApi = new mw.Api();
    return function(pagename){
        return new Promise(function(resolve, reject){
            mwApi .get({
                action: 'parse',
                page: pagename,
                formatversion: 2
            }).then(function(data){
                resolve(data.parse.displaytitle, data.parse.text);
            }, function(e){
                reject(e);
            });
                       
        });
    }
})();
var setLoading = function(boolean){
    // 이미 로딩 완료된 작업의 경우 로딩창을 표시하지 않기 위해
    // 로딩창 표시 작업시 예약 플래그를 설정하고 약간의 텀을 두기
    // 로딩창 삭제 작업시 표시작업이 예약되어있으면 같이 삭제
}
// 선행로딩된 페이지들
// 선행로딩된 페이지들
var documentPromiseMap = {
var documentPromiseMap = {};


};
var namespace = $("#firstHeading > span.mw-page-title-namespace").val() || ""
var namespace = $("#firstHeading > span.mw-page-title-namespace").val()
// 해당 링크의 action, title, oldid 파라미터가 없는 링크만 가져오기
// 해당 링크의 action, title, oldid 파라미터가 없는 링크만 가져오기


targetLinks = $("#mw-content-text a").not(".external").filter(function() {
var targetLinks = $("#mw-content-text a").not(".external").filter(function() {
     return !this.href.match(/action=|title=|oldid=/);
     return !this.href.match(/action=|title=|oldid=/);
}).toArray().map(function(el) {
}).toArray().map(function(el) {
24번째 줄: 49번째 줄:
.filter(({namespace:thisNamespace}) => thisNamespace === namespace )
.filter(({namespace:thisNamespace}) => thisNamespace === namespace )
// 필터된게 previewLimit 갯수 이상이면 동작 x, 프로미스맵에 클릭 시 로딩 필요함을 명시
// 필터된게 previewLimit 갯수 이상이면 동작 x, 프로미스맵에 클릭 시 로딩 필요함을 명시
// 필터링된게 프로미스맵에 없는 경우 사전 프리로딩 프로미스 추가
if(targetLinks.length > previewLimit){
// a링크 href를 #로 변경, 클릭 시 이벤트 바인딩
    targetLinks.forEach(({link}) => documentPromiseMap[link] ||= null);
     // 프로미스맵에서 해당 링크에 바인딩된 프로미스 확인
} else {
     // 프리로드 불필요한 경우(네임스페이스가 다를때, 편집/리비전확인 링크일때) url 영구이동
    // 필터링된게 프로미스맵에 없는 경우 사전 프리로딩 프로미스 추가
    // 프리로드되지 않은 이동 가능한 링크면 로딩창 표시 후 해당 페이지 로딩
    targetLinks.forEach(({link, docname, namespace}) => {
    // 링크 프로미스에 문제가 있을 시 다시 내용 확인, 성공시 문서 프로미스에 저장, 오류시 에러메세지
        var pagename = docname === "" ? namespace : `${namespace}:${docname}`;
    // 로딩완료되면 로딩창 삭제
        documentPromiseMap[link] ||= getParsedDocumentPromise(pagename)
        // 프리로드 프로미스가 정상적으로 불러왔을 경우
    });
        // Promise.race1
}
            // 문서내용 페이드 아웃,  
 
            // 프로미스 내용으로 교체
// 가져온 링크로 전체 작업
            // 문서내용 페이드 인
targetLinks.forEach(function(this){
        // Promise.race2
    var $link = $(this);
            // 사전로딩된 내용에서 프리로드 분석 재실행
    // a링크 href를 #로 변경, 클릭 시 이벤트 바인딩
     var href = $link.attr("href");
    var documentPromise = documentPromiseMap[href];
     $link
        .attr("href", "#")
        .click(function(){
 
            // 프리로드 불필요한 경우(네임스페이스가 다를때, 편집/리비전확인 링크일때) url 영구이동
            if(documentPromise === undefined){
                return location.href = href;
            }
            // 프리로드되지 않은 이동 가능한 링크면 로딩창 표시 후 해당 페이지 로딩
            if(documentPromise === null){
                documentPromise = getParsedDocumentPromise(href);
            }
 
            // 프로미스가 아직 안끝났으면 로딩창 표시
            setLoading(true);
            // 링크 프로미스에 문제가 있을 시 다시 내용 확인, 성공시 문서 프로미스에 저장, 오류시 에러메세지
            documentPromise.then(function(title, text){
                // 프리로드 프로미스가 정상적으로 불러왔을 경우
 
                // Promise.race1
                    // 문서내용 페이드 아웃,  
                    // 프로미스 내용으로 교체
                    // 문서내용 페이드 인
                // Promise.race2
                    // 사전로딩된 내용에서 프리로드 분석 재실행
            }).error(function(e){
                // 에러 발생 시 실패한 페이지 다시 프로미스에 저장 시도
                documentPromiseMap[href] = null;
                documentPromise = null;
 
                // 에러메세지 표시
                toast('페이지 로딩에 실패했습니다. 다시 시도해주세요.');
 
            }).finally(function(){
                // 로딩창 삭제
                setLoading(false);
            });
        });
    })
})

2023년 7월 6일 (목) 23:15 판

// 프리로딩 가능한 링크 최고 갯수 var previewLimit = 5 var getParsedDocumentPromise = (function(link){

   var mwApi = new mw.Api(); 
   return function(pagename){
       return new Promise(function(resolve, reject){
           mwApi .get({
               action: 'parse',
               page: pagename,
               formatversion: 2
           }).then(function(data){
               resolve(data.parse.displaytitle, data.parse.text);
           }, function(e){
               reject(e);
           });
                       
       });
   }

})();

var setLoading = function(boolean){

   // 이미 로딩 완료된 작업의 경우 로딩창을 표시하지 않기 위해
   // 로딩창 표시 작업시 예약 플래그를 설정하고 약간의 텀을 두기
   // 로딩창 삭제 작업시 표시작업이 예약되어있으면 같이 삭제

}

// 선행로딩된 페이지들 var documentPromiseMap = {};

var namespace = $("#firstHeading > span.mw-page-title-namespace").val() || "" // 해당 링크의 action, title, oldid 파라미터가 없는 링크만 가져오기

var targetLinks = $("#mw-content-text a").not(".external").filter(function() {

   return !this.href.match(/action=|title=|oldid=/);

}).toArray().map(function(el) {

   var [_, namespace, docname] = decodeURI(el.href).match(/[a-z]+\:\/\/[a-z\.]+\/[a-z\.]+\/([^\:]+)\:?(.*)/);
   if (docname === "") [namespace, docname] = [docname, namespace];
   [namespace, docname];
   
   return {
       el,
       link: el.href,
       title: el.title,
       namespace, docname
   }

}) // 동일한 네임스페이스만 이동되게 필터링 .filter(({namespace:thisNamespace}) => thisNamespace === namespace ) // 필터된게 previewLimit 갯수 이상이면 동작 x, 프로미스맵에 클릭 시 로딩 필요함을 명시 if(targetLinks.length > previewLimit){

   targetLinks.forEach(({link}) => documentPromiseMap[link] ||= null);

} else {

   // 필터링된게 프로미스맵에 없는 경우 사전 프리로딩 프로미스 추가
   targetLinks.forEach(({link, docname, namespace}) => {
       var pagename = docname === "" ? namespace : `${namespace}:${docname}`;
       documentPromiseMap[link] ||= getParsedDocumentPromise(pagename)
   });

}

// 가져온 링크로 전체 작업 targetLinks.forEach(function(this){

   var $link = $(this);
   // a링크 href를 #로 변경, 클릭 시 이벤트 바인딩
   var href = $link.attr("href");
   var documentPromise = documentPromiseMap[href];
   $link
       .attr("href", "#")
       .click(function(){
           // 프리로드 불필요한 경우(네임스페이스가 다를때, 편집/리비전확인 링크일때) url 영구이동
           if(documentPromise === undefined){
               return location.href = href; 
           }
           // 프리로드되지 않은 이동 가능한 링크면 로딩창 표시 후 해당 페이지 로딩
           if(documentPromise === null){
               documentPromise = getParsedDocumentPromise(href);
           }
           // 프로미스가 아직 안끝났으면 로딩창 표시
           setLoading(true);
           // 링크 프로미스에 문제가 있을 시 다시 내용 확인, 성공시 문서 프로미스에 저장, 오류시 에러메세지
           documentPromise.then(function(title, text){
               // 프리로드 프로미스가 정상적으로 불러왔을 경우
               // Promise.race1
                   // 문서내용 페이드 아웃, 
                   // 프로미스 내용으로 교체
                   // 문서내용 페이드 인
               // Promise.race2
                   // 사전로딩된 내용에서 프리로드 분석 재실행
           }).error(function(e){
               // 에러 발생 시 실패한 페이지 다시 프로미스에 저장 시도
               documentPromiseMap[href] = null;
               documentPromise = null;
               // 에러메세지 표시
               toast('페이지 로딩에 실패했습니다. 다시 시도해주세요.');
           }).finally(function(){
               // 로딩창 삭제
               setLoading(false);
           });
       });
   })

})