약년 2: 위챗 애플릿의 웹 구현

10401 단어
위챗 애플릿을 접한 이래로 웹에 애플릿을 넣고 실행하기를 바랐지만, 자신은 VirtualNode, React 등에 익숙하지 않아 천천히 공부할 수밖에 없었다.
요 며칠 동안 React-Native를 자주 사용해서 작은 앱을 만들어 연습한다.하지만 많은 어려움을 겪었다.예를 들어android의 많은 구성 요소가 완전하지 않은 문제는 모두git,npm가 찾아서 로컬 모듈을 써야 합니다..개발 효율은 저폭이라고 할 수 있다.
읽은 자료:
노트 1 위챗 애플릿이 크롬 브라우저에서 실행되도록 합니다
그 중에서 그것이 마이크로 소스 코드에 대한 분석을 소개했다.미리 보기 GitHub:https://github.com/phodal/weapp-webdemo미리 보기:http://weapp.phodal.com/
위챗 애플릿의 3대 구성 요소 처리 방법
js wxml과 wcss
js가 패키지로 봉인됨
define("app.js", function(require, module){var window={Math:Math} //   babel/
,location,document,navigator,self,localStorage,history,Caches; App({ onLaunch: function () {
//     xx.js   
  }
    })
}); require("app.js"); 

wxml이 function, 즉 js 파일로 변환됨
이것은 react의 jsx와 유사할 것입니다.라고 적었다.이 작업은 위챗 웹 개발자 도구\package.nw\app\dist\weapp\onlinevendor 디렉토리의 wcc를 사용하여 수행할 수 있습니다.
/*v0.7cc_20160919*/
var $gwxc
var $gaic={}
$gwx=function(path,global){
function _(a,b){b&&a.children.push(b);}
function _n(tag){$gwxc++;if($gwxc>=16000){throw 'enough, dom limit exceeded, you don\'t do stupid things, do you?'};return {tag:tag.substr(0,3)=='wx-'?tag:'wx-'+tag,attr:{},children:[]}}
function _s(scope,env,key){return typeof(scope[key])!='undefined'?scope[key]:env[key]}
function _wl(tname){console.warn('template `' + tname + '` is being call recursively, will be stop.')}
function _ai(i,p,e,me){var x=_grp(p,e,me);if(x)i.push(x);else{console.warn('path `'+p+'` not found from `'+me+'`')}}
function _grp(p,e,me){if(p[0]!='/'){var mepart=me.split('/');mepart.pop();var ppart=p.split('/');for(var i=0;i

wcss css로 전환
상기 디렉터리에 있는 wcsc 파일을 사용하면 css 파일로 변환할 수 있습니다. $gwx 함수의 주요 용도는 바로 구조 인터페이스이다.다음 코드에서 호출됨
javascript
document.dispatchEvent(new CustomEvent("generateFuncReady", {
detail: {
generateFunc: $gwx('index.wxml')
}
}))

위챗 라이브러리는 어디에 있습니까?
WXWebview에서.js에서, 그러나 이 파일은 포장된 파일입니다.
분리는 이런 define.js, 여기가 AMD 모듈화를 정의하는 곳exparser입니다.js, WXML 태그를 HTML 태그 exparser-behvaior로 변환하는 데 사용합니다.js, 서로 다른 탭의 행동을 정의합니다.js, 이벤트 라이브러리일 거예요. 관심 없는 것 같아요.page.js, 핵심 코드, 즉 페이지, 앱의 정의가 있는 곳.report.js, 네가 말한 모든 것을 너의 법정에 출두하여 진술할 수 있다.virtual_dom.js, 하나의virtualdom는 wcc와 결합하여 사용할 수 있으며, 그 안에는component도 있을 것이다.css, weui wa-wx라고 할 수도 있습니다.js, 위챗의 각종 API와 WebView와 Native를 정의하는 곳은 아래의 WX와 충돌합니다.wx.js, 동상이지만 약간 다르다.wxJSBridge.js, Weixin JS Bridge(참조http://www.tuicool.com/articles/juquYfy)
렌더링 프로세스
먼저 Custom Event 보내기(참조https://developer.mozilla.org/zh-CN/docs/Web/API/CustomEvent/CustomEvent). 이 이벤트는 아래 함수에 의해 받아들여지고 처리됩니다
document.addEventListener("generateFuncReady", function (e) {
var generateFunc = e.detail.generateFunc; //    $gwx         
wx.onAppDataChange && generateFunc && wx.onAppDataChange(function (e) { //     ,           
var i = generateFunc((0, d.getData)()); //          (  d     ?      ,  Page  data  )
if (i.tag = "body", e.options && e.options.firstRender){ //        
e.ext && ("undefined" != typeof e.ext.webviewId && (window.__webviewId__ = e.ext.webviewId), "undefined" != typeof e.ext.downloadDomain && (window.__downloadDomain__ = e.ext.downloadDomain)), v = f(i, !0), b = v.render(), b.replaceDocumentElement(document.body), setTimeout(function () {
wx.publishPageEvent(p, {}), r("firstRenderTime", n, Date.now()), wx.initReady && wx.initReady()
}, 0);
} else {
var o = f(i, !1), a = v.diff(o);
a.apply(b), v = o, document.dispatchEvent(new CustomEvent("pageReRender", {}));
}
})
})

이 함수는 먼저 e.detail을 얻었습니다.바로 Custom Event의 두 번째 매개 변수입니다. 우리가 준 대상입니다.그리고generateFunc라는 함수를 가져왔습니다. 이 함수는 앞에서 정의한 $gwx ('index.wxml') 의 반환값 (함수일 수도 있습니다), 즉 인터페이스 렌더링 함수입니다.
하면, 만약, 만약...onAppDataChange가 비어 있지 않으며generateFunc도 비어 있지 않습니다. 그러면 터치 함수를 onAppDataChange에 추가합니다.이 함수에서generateFunc를 호출해서 인터페이스를 가져왔습니다. i는dom트리일 것입니다.i에 tag를 body로 정의합니다.그리고 첫 번째 렌더링이라면...뒤에 diff와 apply가 있는데 대체로 뜻을 알 수 있어요...전체적으로 잘 못 봤어요.
마지막으로git에서 준 데모는 뛰지 않았고 뛰쳐나온 것은 공백이었다.
다른 파일을 읽으면 $gwx ('test.wxml ') 는 정확한 wxml 파일 이름과 경로를 제시해야만 파일을 만들 수 있고, 이 함수를 호출하면 json이 생성됩니다.
이런 디자인은 js 파일에 모든 wxml을 포함할 수 있도록 설계된 것이다.
미나의 위챗 애플릿 호환 프레임워크
또한 지난 글과 같은 작가가 위챗의 구조를 연구한 후에 작은 프로그램의 호환 구조를 스스로 실현하기로 결정했다.이 프레임은github에 있어요.https://github.com/phodal/winv
이 글을 삼가 읽었습니다.그중의 코드를 읽었습니다. 현재 이 프레임워크는 간단한 데모일 뿐입니다.
이것은 winv입니다.js의 코드...어, 이 이름을 지은 건 미나가 거꾸로...악취미.제가 주석을 좀 넣었어요.
window.eventPool = [];
window.globalData = {};
const winv = {
  parser() {

  },
  components: [{

  }],
  setTemplate(template){  //wxml       
    this.template = template;
  },
  appRun() {
    var template = this.template;
    var domJson = this.stringToDomJSON(template)[0];  // wxml       json
    var dom = this.jsonToDom(domJson);  // json      dom 
/**
                     ?        。
                   ,               tag。       tag
                    {{}}      ?
**/
    document.getElementById('app').appendChild(dom);
    for (var event in window.eventPool) {
      window.eventPool[event]();
    }
  },
  Page (options) { //         Page  ,       。 option               
    for (var option in options) { //              
      if ('on' === option.slice(0, 2)) { //   on   ,       。
        window.eventPool.push(options[option]); //   eventPool   ?     。。。。
      }
      if ('data' === option) { //   data,    globalData 。             。。。
        window.globalData = options[option];
      }
    }
  },
  App (options) {
    for (var option in options) {
      if ('on' === option.slice(0, 2)) { //     ,     
        window.eventPool.push(options[option]);
      }
    }
  },
  getData: function updateData(key) { //    
    return window.globalData[key];
  },
  utils: { //      
    removeTemplateTag(str){
      return str.substr(2, str.length - 4);
    },
    isTemplateTag(string){  
      return /{{[a-zA-Z1-9]+}}/.test(string);
    }
  },
  stringToDomJSON(string){ //     ,      json
    string = '
' + string + '
'; var json = this.nodeToJSON(this.domParser(string)); if (json.nodeType === 9) { json = json.childNodes; } return json; }, domParser(string){ // js DomParser dom var parser = new DOMParser(); return parser.parseFromString(string, 'text/xml'); }, nodeToJSON(node){ // , dom json // Code base on https://gist.github.com/sstur/7379870 node = node || this; var obj = { nodeType: node.nodeType }; if (node.tagName) { // tag , winv- obj.tagName = 'winv-' + node.tagName.toLowerCase(); } else if (node.nodeName) { obj.nodeName = node.nodeName; } if (node.nodeValue) {// , , , 。 // ! if for, 。 obj.nodeValue = node.nodeValue; if(this.utils.isTemplateTag(node.nodeValue)){ obj.nodeValue = this.getData(this.utils.removeTemplateTag(node.nodeValue)); } } var attrs = node.attributes; if (attrs) { var length = attrs.length; var arr = obj.attributes = new Array(length); for (var i = 0; i < length; i++) { var attr = attrs[i]; arr[i] = [attr.nodeName, attr.nodeValue]; } } var childNodes = node.childNodes; if (childNodes) { length = childNodes.length; arr = obj.childNodes = new Array(length); for (i = 0; i < length; i++) { arr[i] = this.nodeToJSON(childNodes[i]); // , } } return obj; }, jsonToDom(obj) //JSON dom。 。。。react diff ? react 。 { // Code base on https://gist.github.com/sstur/7379870 if (typeof obj == 'string') { obj = JSON.parse(obj); } var node, nodeType = obj.nodeType; switch (nodeType) { case 1: //ELEMENT_NODE node = document.createElement(obj.tagName); var attributes = obj.attributes || []; for (var i = 0, len = attributes.length; i < len; i++) { var attr = attributes[i]; node.setAttribute(attr[0], attr[1]); } break; case 3: //TEXT_NODE node = document.createTextNode(obj.nodeValue); break; case 8: //COMMENT_NODE node = document.createComment(obj.nodeValue); break; case 9: //DOCUMENT_NODE node = document.implementation.createDocument('http://www.w3.org/1999/xhtml', 'html', null); break; case 10: //DOCUMENT_TYPE_NODE node = document.implementation.createDocumentType(obj.nodeName); break; case 11: //DOCUMENT_FRAGMENT_NODE node = document.createDocumentFragment(); break; default: return node; } if (nodeType == 1 || nodeType == 11) { var childNodes = obj.childNodes || []; for (i = 0, len = childNodes.length; i < len; i++) { node.appendChild(this.jsonToDom(childNodes[i])); } } return node; } }; export default winv;

사용법



    
    Winv Demo
    
    


var App = winv.App; var Page = winv.Page; App({ onLaunch: function() { console.log('On Launch'); } }); Page({ data: { motto: 'hello, world' }, onLoad: function() { console.log('On Load'); } }); winv.setTemplate('<view class="container"><text class="user-motto">{{motto}}</text></view>') winv.appRun();

그래도 wx 닮았어.App、Page、wxml(template)
이 winx 프레임에 대해서.
전체적으로 보면 이 프레임워크는 장난감 프레임워크로 위챗 애플릿의 처리 절차를 보여주지만 실제 제품과는 거리가 멀다.
첫째: 한 페이지만 지원합니다.둘째: 페이지의 모든 이벤트 처리가 정돈되지 않았다.셋째, 실행 기간에 분석을 하고 프로그램의 원본 코드가 모두 포함되어 있다.(.wxml 파일), 원본 보호에 불리합니다.
나는 어제 이 프로젝트에 몇 가지 코드를 공헌했고 {{obj.name}}이라는 문법 지원을 추가했다.
나는 이 틀에서 계속해야 할지 말지를 고려하고 있다.스스로 틀을 세울지.리얼리티를 포장해 볼까요?아니면 웹팩으로만 직접 diff와 apply를 쓸까요?
읽을래 읽지 않은 글 목록
http://www.tuicool.com/articles/aQNbUzI

좋은 웹페이지 즐겨찾기