2016年7月29日 星期五

到數計時效果


//方式1:用jquery過場動畫

var jqDivContainer = $('#divContainer');

function countdown(time){
    jqDivContainer.prepend('<h1 id="h1Countdown"></h1>').css('position', 'relative');
    var jqH1Countdown = $('#h1Countdown');
    jqH1Countdown.css({
        color:'white',
        'line-height': '300px',
        width: '100%',
        'text-align': 'center',
        'margin-top': 0,
        'font-size': 64,
        position: 'absolute',
    });

function repeat(time){
        jqH1Countdown.text(time);
       
        jqH1Countdown.fadeIn(500,'swing',function(){
            jqH1Countdown.fadeOut(500,'swing',function(){
                time--;
                if (time > 0) repeat(time);
                else {
                    jqH1Countdown.remove();
                    jqDivContainer.css('position', 'static');
                }
            });
        });
    }

    repeat(time);

}

countdown(10);

點我看demo

//方式2:用css transition

var jqDivContainer = $('#divContainer');

function countdown(time){
    jqDivContainer.prepend('<h1 id="h1Countdown"></h1>').css('position', 'relative');
    var jqH1Countdown = $('#h1Countdown');
    jqH1Countdown.text(time).toggleClass('show');
    function repeat(time) {
        setTimeout(function(){
            var isShowing = jqH1Countdown.hasClass('show');
            if(!isShowing) time--;
            if(time > 0){
                if(!isShowing) jqH1Countdown.text(time);
                jqH1Countdown.toggleClass('show');
                repeat(time);
            }else {
                jqH1Countdown.remove();
                jqDivDrawingJumbo.css('position', 'static');
            }
        },500);
    }

    repeat(time);


}

countdown(10);

點我看demo

2016年7月22日 星期五

asp web MVC memo

App_Start資料夾裡的RouteConfig.cs 設定起始controller,並指定於該controller內的起始action

每個controller在Views資料夾中都有一個對應名稱的資料夾
裡面置放對應controller的action的view檔案

於action中可以do  something you want 並傳遞內容至view,在view裡面可以用razor語法取值做處理

在Views資料夾裡有一個_ViewStart檔案可以指定view母版,於母版中可用razor語法 @RenderBody()  將view置入

2016年7月12日 星期二

php namesapce 概念 用法 範例

//namespace是用來區隔識別id,例如常數、函數、類別名稱,但不包含變數
//namespace是以' \ ' 模擬階層概念
//預設的namespac是' \ ',所有其他自定義namespace都是歸在其底下,可以省略,
//所以未使用自定義namespace的一般php檔案,識別名稱都不需要加' \ ',但要加也行
//要注意開頭未加上' \ ' 表示相對namespace位置,有加' \ '表示絕對namespace位置
//首個自定義namespcae必須是php檔案的第一列有效程式碼

//關鍵字 'use' 可替過長的命名空間中的 '類別 (class)' 定義簡寫,亦可取別名 (alias),
//例如 use a\b\c\Cat 如此即可以Cat存取到目標 ; use a\b\c\Cat as nsCat 如此即可以nsCat存取到目標
//use 定義即使不加' \ '亦是絕對namespace位置
//namespace參考資料 : http://pydoing.blogspot.tw/2013/03/PHP-namespace.html

//使用外部檔案以include或require引入,
//等同在指定位置貼上該檔案程式碼片段,但其namespace定義已完成,不會在引入處再次作用,除此之外namespace運作規則不變
//include與require差異參考資料: http://syunguo.blogspot.tw/2013/04/phpinclude-require.html

//當類別庫愈來愈完整,需要引入的檔案就愈多,一個一個引入太沒效率,這時可使用autoload功能
//autoload功能參考資料: http://justericgg.logdown.com/posts/196891-php-series-autoload

//以下namespace使用簡例

//定義namespace
namespace a\b\c;
//於其中定義識別名稱,此處以常數為例
const Demo = 2;

//定義另一個namespace
namespace a\b;
const Demo = 1;
$test = 3;
//存取常數內容

//相對namespace位置,以最近的namespace為所在位置指定識別名稱,類似 '目前資料夾' 概念,
//於特定namespace中以相對namespace位置指定識別名稱時要注意階層關係
echo Demo;
echo c\Demo;
//絕對namespace位置,以完整namespace階層指定識別名稱,類似 '資料夾絕對路徑' 概念
echo \a\b\Demo;
echo \a\b\c\Demo;

2016年7月4日 星期一

OOP 物件導向 用不同的方式理解instance(實體,實例)

物件導向中,instance一般稱為實例、副本,或稱之為實體

所謂instance就是實際在記憶體佔有位置的物件,以new關鍵字創造instance時,是在記憶體畫一塊空間給該物件,儲存該物件的相關資訊,每個屬性和方法都在該空間佔有一席之地,儲存對應的值

在使用new關鍵字建立新的instance時,需給予一個變數儲存其指標,例如:

var obj = new Object( );

在javascript中,上列語法等同下列:

var obj = {};

' { } ' 這個大括弧就好像在記憶體上畫一塊地,說這是我的地盤,需要注意的是obj代表的只是這塊地的地圖,而不是這塊地本身

obj.name = '';
obj.age = '';

這就好比是在自己的地盤上再切割小的區塊,並分別為其取名為name和age

obj.name = 'Ryu';
obj.age = 33;

接著我們在name區塊上寫下Ryu這三個字,在age區塊上寫下33這個數字

var map = obj;

這並未在記憶體上再畫一塊地給map,而只是將地圖複製了一份到map上

map 和 obj指向的都是同一塊地,這塊地有著name和age兩個區域

obj = '';

這清除了存放在obj中的地圖,無法再使用它找到那塊地,但那塊地依然存在

obj.name

找不到那塊地,自然也找不到name區域

map.name

還好,有先備份了一份地圖,還可以靠它找到那片土地,找到其中的name區域,並取得寫在該區域上的東西

obj = new Object();

接著我們在記憶體上畫了一塊新的空地,並把地圖放進obj中

現在我們總共擁有兩塊地了,並分別將位置記錄在map和obj這兩個變數中

map = '';

一不小心,弄丟了其中一塊地的地圖,其僅存的一張地圖,從此我們再也無法到達那塊地了,也無法再看到那塊地有哪些區域,以及區域上寫些什麼了

雖然我們已經不知道如何到達那塊地,但它一直都在那裡,過了一陣子,土地管理者(garbage collector)發現這塊地無人使用,也沒有任何地圖指向它,便再度開放給有需要的人使用了





2016年7月2日 星期六

javascript 物件導向 繼承 運作方式 prototype chain 範例

//以下以實例說明javascript的物件導向繼承運作方式


//定義動物類別
function Animal (weight, height, numLegs) {
    this.weight = weight;
    this.height = height;
    this.moveable = true;
}

//定義狗類別
function Dog (name) {
    this.name = name;
    this.setName = function (name){
        this.name = name;
    };
}

//創造一個狗類別實體
var laifu = new Dog('laifu');

//透過類別的prototype新增吠叫方法,這可以直接讓既存的實體擁有吠叫的能力

Dog.prototype.bark = function (){
    console.log('woof!');  
};

laifu.bark();
//可使用bark方法
//因為實體會透過prototype chain"向上"從祖先的prototype中尋找可用的方法與屬性
//實體的__proto__屬性儲存著所屬類別的prototype內容,
//所屬類別的prototype的__proto__屬性儲存著父類別的prototype內容
//向上延伸直至原始類別Object的prototype,再往上就是null
//實際運作過程是使用new創建實體時會run一遍prototype chain,取得可用的屬性和方法,
//相同的屬性或方法以血緣近者優先取用
//可透過右側方式探索prototype chain: laigu.__proto__.__proto__...

//讓狗類別繼承Animal類別
Dog.prototype = new Animal();
//此時Dog.prototype指向的記憶體位置已不同,已是指向Animal類別的一個實體,值已從原本的{bark:function(){}}變成{weight:undefined, height:undefined, ...},而Dog.prototype.__proto__指向的是其父類別的prototype,也就是Animal.prototype

laifu.bark();
//laifu.__proto__指向的仍是原本的記憶體位置,也就是原本的Dog.prototype,值是{bark:function(){}},所以仍然可使用bark方法

//創造另一個狗類別實體
var littleBlack = new Dog('littleBlack');

//littleBlack.bark();已無法使用這個方法,因為littleBlack.__proto__指向的Dog.prototype已是新的位置,有新的值{weight:undefined, height:undefined, ...}

console.log(littleBlack.moveable);//繼承後新建的實體依循新的prototype chain取得moveable這個屬性
console.log(laifu.moveable);//繼承前既存的實體仍是依循原本的prototype chain,其中沒有moveable這個屬性,所以輸出undefined

//定義一個新的黃金獵犬類別

function GoldenRetriever() {
    this.hunt = function () {
        console.log('It\'s hunting');  
    };
}

//繼承狗類別
GoldenRetriever.prototype = new Dog();

var littleGold = new GoldenRetriever();

//實體littleGold透過littleGold.__proto__,也就是GoldenRetriever.prototype獲得name屬性並習得setName方法
//以下內容值驗證,後續的console.log都是在驗證內容值
console.log(littleGold.__proto__);
console.log(GoldenRetriever.prototype);

littleGold.setName('littleGold');
console.log(littleGold.name);

//透過littleGold.__proto__.__proto__,也就是Dog.prototype獲得moveable屬性
console.log(littleGold.__proto__.__proto__);
console.log(Dog.prototype);
console.log(littleBlack.__proto__);

console.log(littleGold.moveable);

//使用自己的方法
littleGold.hunt();

//使用prototype動態新增屬性與方法,會即時套用至prototype chain上所有既存實體
Animal.prototype.p1 = 'p1';
Dog.prototype.p2 = function (){console.log('p2')};
GoldenRetriever.prototype.p3 = 'p3';

console.log(littleGold.p1);
littleGold.p2();
console.log(littleGold.p3);


//相同的屬性或方法,血緣近者優先取用
Animal.prototype.lol = '789';
Dog.prototype.lol = '456';
GoldenRetriever.prototype.lol = '123';

console.log(littleGold.lol);

//輸出prototype chain尾端類別實體擁有的全部屬性和方法
for(prop in littleGold){
    console.log(prop); 
}

//分界線
console.log('-------------------------------');


//private 屬性和方法,物件中以this定義的屬性和方法為public,以var定義者為private
//private 屬性和方法不會在for in迴圈中顯示
function Person(name, age, weight){
    //public
    this.name = name;
    this.say = function (words){
        console.log(this.name + ' says ' + words + '.');
    };
    //private
    var age = age;
    var weight = weight;
    var think = function(question){
        return ('I think ' + question + ' is a great thing.');
    };
    //使用public方法存取private屬性和方法
    this.setAge = function (num){
        age = num;
    };
    this.tellingAge = function (friendship){
        if(friendship === 'good') return age;
        else return 'this is secret.';
    };
    this.tellingWeight = function (friendship){
        if(friendship === 'good') return weight;
        else return 'this is secret.';
    };
    this.advise = function (friendship){
        if(friendship === 'good') return think;
        else return 'sorry I have no time.';
    };
}

var Ryu = new Person('Ryu',36,75);

for(p in Ryu){
    console.log(p);
}

console.log(Ryu.name);
Ryu.say('hello!');
console.log(Ryu.tellingAge('good'));
console.log(Ryu.tellingWeight('normal'));

var thinkingMethod = Ryu.advise('good');
var thought = thinkingMethod('OOP');

console.log( thought );
console.log( thinkingMethod('OOP') );
console.log( Ryu.advise('good')('OOP') );

console.log('------------------------------');

//定義rosyPerson類別
function rosyPerson (mentality) {
    this.mentality = mentality;
    var hardshipExp = 'many years ago...';
    this.tellingStory = function (){
      return hardshipExp;  
    };
}

//繼承Person類別,private屬性和方法一樣會繼承
rosyPerson.prototype = new Person();

var rosyKen = new rosyPerson('positive');

for(p in rosyKen){
    console.log(p);
}

console.log( rosyKen.advise('good')('programming') );
rosyKen.setAge(33);
console.log( rosyKen.tellingAge('good') );

//所有物件皆繼承原始物件Object,因此擁有Object.prototype中的所有屬性和方法,例如hasOwnProperty方法
//可透過console.log(Object.prototype)檢視有哪些通用的方法和屬性
console.log(Object.prototype);

//hasOwnProperty方法確認是否擁有指定的屬性或方法,傳回true或false,繼承的屬性或方法會傳回false,
//private 屬性和方法也會傳回false

console.log(rosyKen.hasOwnProperty('mentality'));
console.log(rosyKen.hasOwnProperty('name'));
console.log(rosyKen.hasOwnProperty('hardshipExp'));
console.log(rosyKen.hasOwnProperty('tellingStory'));
console.log(rosyKen.tellingStory());


//打完收工

2016年7月1日 星期五

CSS 動畫 行星效果





























範例實作程式碼

範例參考:Codecademy