留言板小程序开发笔记3

在vim中的 "删除到" 命令, 使用 dt"关键字符", 这里的关键字符 包括: "space"空格, 这个是很强大,很有用的~

如果严格地写代码, 那么, 在定义自己的controller类的时候, 里面的函数方法, 还是 应该明确的 写成public, protected, private等访问权限方式!

如果使用tp, 则导入:外部的css和js, 可以使用tp的简化方式:

  1. import标签, 指明 type属性, 和file属性.
    type指明是css还是js, 默认是js可以不写.
    file指明文件的时候, 路径直接从 /Public/写起, 而且不用写扩展名, 因为前面已经指明了文件类型的
    由于 import是类似 Think的命名空间函数, 所以 在写路径的时候, 要用点号而不用 斜杠;

  2. load 或 css js标签
    这个就很简单直接了:
    直接就只是一个 href属性就行了. 直接写完整路径就好了.
    ...


获取 系统输入变量值 (这里仅仅是针对 系统变量的 "获取输入值")

  1. 传统的方式是直接使用 $_GET, $_POST 等 但是这个方式不安全, 因为没有安全过滤方式
  2. 所以, 既然使用的是tp, 就要用tp的方式去获取系统变量.(自定义变量的值需要自己去定义..)
  3. 要获取系统变量的值, 这里主要指的是 $_GET, $_POST, 就 用 I 函数.
  4. I函数 的语法是: I('变量类型.变量名', ['默认值'], ['过滤函数'])
  5. 即使你不写过滤函数, tp也给你定义了 默认 的过滤函数: 'DEFAULT_FILTER' => 'htmlspecialchars'.所以它 的安全机制就在这里. 当然你也可以自己写自己的过滤函数.

  6. 通常的写法是: I('post.editorValue'). 系统变量的 类型不分大小写, 而变量本身 要严格区分大小写. get和post可以用param来表示, 而默认的类型就是param, 所以如果是get或post, 可以不写变量类型, 直接就是 I('变量名称').


很重要的一点是, 使用 百度在线编辑器的时候, 请使用 Ueditor的版本, 不要使用 Umeditor的版本. 我原来使用umeditor就没有出来, 而是要ueditor的版本就顺利出来了.

如何禁用ueditor自动保存功能?

有两种方法,
一是, 从 ueditor.all.js的 23910行 - 到 - 24038行, 注释掉, 就好了: 即注释掉 UE.plugin.register('autosave', function()...
821299-20170303180643735-1027798084.png
二是, 将saveInterval 的时间设置得 大些
821299-20170303180910423-1749120565.png
如 设置: `saveInterval: (606024*1000) (单位是ms)


关于Xss攻击和xss白名单过滤
跨站脚本攻击(也称为XSS)指利用网站漏洞从用户那里恶意盗取信息。 用户在浏览网站、使用即时通讯软件、甚至在阅读电子邮件时,通常会点击其中的链接。 攻击者通过在链接中插入恶意代码,就能够盗取用户信息。 攻击者通常会用十六进制(或其他编码方式)将链接编码,以免用户怀疑它的合法性。 网站在接收到包含恶意代码的请求之后会产成一个包含恶意代码的页面, 而这个页面看起来就像是那个网站应当生成的合法页面一样。 许多流行的留言本和论坛程序允许用户发表包含HTML和javascript的帖子。 假设用户甲发表了一篇包含恶意脚本的帖子,那么用户乙在浏览这篇帖子时, 恶意脚本就会执行,盗取用户乙的session信息

人们经常将跨站脚本攻击(Cross Site Scripting)缩写为CSS, 但这会与层叠样式表(Cascading Style Sheets, CSS)的缩写混淆。 因此有人将跨站脚本攻击缩写为XSS。如果你听到有人说 “我发现了一个XSS漏洞”,显然他是在说跨站脚本攻击。

过滤xss 通常的 javascript脚本攻击, 是过滤掉 双引号和 尖括号, 但是也不是完全的, 还有很多种方法进行 xss攻击.

也就是说, 当你点击一个外部的(cross site)站点时, 这个 页面会执行一些js脚本, 而这个脚本会"悄悄的"执行, 它不会有什么输出和弹出框, 但是实际上它的代码 是在和你的站点之间进行交互, 如发生数据, 请求和响应信息, 从而盗取你的站点上的cookie / session 中的信息...


为什么表单元素的jquery选择器要直接用冒号 :选择器?
因为表单元素用input type="..."的较多, 如果还是用属性选择器, 就会显得比较麻烦, 所以就直接用 冒号选择符来选择了, 如: $(':submit')

注意, ueditor提供的api等函数, 是供前端页面使用的, 后台php页面是没有办法使用这些函数api的

在使用一些外部的框架的时候, 如果要"排错/debug/修改功能"时, 可以 在外部css/js中调整, 也可以 直接修改 源代码!

ue和um的区别? um是ue的精简版, 主要用在百度贴吧, 其中ue使用的是iframe结构, 而um使用的是div的 结构! 现在使用的较多的是 v1.4.3版本

overflow: 并不是一个固定的整体, 可以分别设置: overflow-x, overflow-y: auto;

如何判断是否有最后一行的空格?
在editplus或vim中有行号的情况下, 如果有空格的空行, 是会显示行号的

对于php文件, 唯一的是 要在 文件的开头, 加上 <?php标签就好了

正则表达式中的 \s \S \b 的区别?
\b表示 border, 边界, 包括 单词/字符的 "开头, 结尾, 空格 回车等 位置", 注意匹配的是位置,不是真的字符, 它不匹配字符的;
\s表示 space, 空格, 是要匹配 "空格字符"的
.点号表示的是任意字符.
表示的是任意个数(包括0个, 即没有)
因此, 如果没有字数限制的话就是 : (.
) 如 a(.*)b可以匹配: ab, a1b, a12b, ...
而 大写的\S则表示 否定的 意思, 即 \S表示 非空字符...

关于thinkphp中的数据库操作?

  1. 增加和更新的区别: 增加记录是add, 而更新记录是save(save表示经过修改后, 再次 "保存" 修改后的内容).看看word 的操作
  2. 不管是什么数据库操作, 都需要有 数据对象. 要创建数据对象, 数据对象可以用 数组或对象 来表示, 要创建数据对象, 可以用 data方法: 即 ->data($data);
  3. add 或 save 方法, 你可以直接传入数据对象, 如 ->add($data); 但是通常的做法是 先创建数据对象, 然后再 直接调用 空 参数的add, 或 save方法: $M->data($data)->add();
  4. 创建对象的方式有两种, 一种是data, 一种是create(create用于直接从 post过来的数据中 创建数据对象).
  5. tp支持多种方式的数据对象, 如: 字符串, 数组, 对象. 但是推荐使用 数组的方式;
  6. 数组的方式有 两种定义: 一种是 采用中括号的方式, 如 $data['msger'] = $msger; .... 的方式, 另一种是 采用 数组定义的方式: $data =array('msger' => $msger, ....); 但是好像 第一种方式比较常用, 但是两者的结果很明显是一样的!

  7. tp数据库操作对字段 的过滤和选择,使用 field方法, 一是, 在select的时候, 使用field方法, 只是查询 你需要的字段, $M->field('f1, f2,f3')->select(); field字段也支持as别名, 对于复杂的别名/聚合函数操作, 就使用数组的方式; 另一种是 和create方法结合使用, 创建数据对象: if($M->field('f1,f2,..) ->create()){$M -> add(); 或 $M -> save(); .....}; 这样即使post有很多字段, 操作时也只有过滤后的字段 被写入. 这样就实现了一种安全机制..

真正理解了tp后, 就要把tp由厚读薄, 先是理解了所有的东西后, 就只是注意掌握和使用最常用的功能就行了!! 其他比较复杂的功能, 只有在遇到的时候, 再去做就行了.

关于注册/登录/发表 等操作成功时, 是否需要给予提示?


建议是:不要提示注册成功, 直接引导用户到 想要进行的操作就好了...
用来注册的 from,当注册成功后,再显示提示信息没有任何意义。
你可以用 很多方法来让引导用户 让他知道已经注册成功了,比如,原来不能下载的,下载链接出现了,原来不能看的内容,现在显示出来了可以。用户注册就是为了继续他未能完成的操作。

在使用thinkphp, 做form表单提交的时候, 最好将处理页面 里面, 写上 $this->display(); 显示对应的 html页面, 否则的话, 会出现" 触发启动 迅雷" 等莫名其妙 的问题?!

thinkphp的success和error方法, 指定自己的 模板文件时, 其调用的模板 的参考起始位置是::: 同一个控制器如, AnnController , 所对应的 View视图目录/控制器名称目录Ann/下的模板文件. 比如, 模板文件参数是 'Public/some' . 就是View/Ann/Public/some.html. 注意, 指定模板文件参数时, 不需要指定html 后缀名.所以, 这里就用的是Public/some, 而不是Public/some.html


非常重要的: 如何在跨 控制器之间 调用方法地址?

  1. 在Home 模块下, 有多个控制器, 如IndexController, AnnController,LoginController. 那么在LoginController控制器的方法 checkLogin中,处理逻辑是: 获取form传过来的值, 然后查询数据库,如果有记录结果, 说明登录成功;
  2. 那么成功后就要跳转: $this->success('跳转提示', '$jumpUrl跳转地址', '等待时间$waitTime' ); 最重要的就是这里的 跳转地址了;
  3. 默认的跳转地址, 如上所说, 调用的模板 的参考起始位置是::: 同一个控制器如, AnnController , 所对应的 View视图目录/控制器名称目录Ann/下的模板文件. , 总是在同一控制器对应的视图View/ControllerName/目录下的html页面;
  4. 要获得 其他/另一 控制器的 方法路径 页面, 就要使用 A方法: A('Index/index');
  5. 要注意A方法和R方法的区别, 好像用R方法还不行???

用tp的where方法时, 条件通常用 $condition 或 $map 来表示, 支持 字符串 和 数组方式, 如果条件中, 有变量的话, 最好还是用 数组的方式. 而且, 使用sprintf的方式, 是为了 格式检查, 增加额外的 安全性, 那么这时, where方法就包含两个参数了, 一个是 "格式字符串", 另一个是 传递的 变量数组...: $M -> where('id=%d and username=%s and passwd=%s', array($id, $username, $passwd))


html中可以使用 页面中的 javascript的变量值.

调用success方法的时候, 自动会调用 ThinkPHP/Tpl/dispatch_jump.tpl, 并将你设置的success参数, 作为模板变量, 传递到 ThinkPHP/Tpl/dispatch_jump.tpl 生成内容输出. 同时, 如果你处理提交的页面, 还调用了 display方法, 那么对应的 方法的视图html内容, 还会接着输出.

对于Application来说, 我们使用的是mvc模式, 提供的是View视图目录.HI

而对于Thinkphp来说, 他的目录使用的是 模板 模板技术, 所以目录是Tpl. 

即 应用程序只有View没有Tpl, 而Thinkphp只有Tpl没有View

ThinkPHP包含的内容:

根下包含的是:

  • Common是全局的 函数functions.php
  • Conf是全局 的配置目录
  • Lang是全局的 语言包
  • Tpl是 全局的 模板目录
  • Library 是核心的库.

但是前面提到的那些, 都是跟 核心库 平级的内容.
核心的Library库目录, 包括: 行为Behavior(实际上就是面向切面的设计模式, 就是对于所有的类对象, 都是一致的 "行为", 封装起来的东西), 开源组织提供的库Org(主要包括Net, Util工具类库), Think提供的核心库, 第三方开发商提供的类库Vendor.


弄清楚thinkphp下的各种路径PATH?

THINK_PATH, 是 ThinkPHP框架的路径; 不是 Library/Think的路径~
LIB_PATH, 是Thinkphp下的库路径, = THINK_PATH.'Library'.'/';
BEHAVIOR_PATH
CORE_PATH, 这个才是Controller,Model, Session等支持mvc模式的类库, 即 Library目录下的 Think目录!
VENDOR_PATH

thinkphp中的 "系统变量"? 

  1. 系统变量, 通常使用在 tp的模板中,
  2. 系统变量是指, $_GET, $_POST, $_SESSION 等, 通常在模板中, 以Think. 开头, 如 Think.get.some_var, Think.post.some_var.
  3. 区分系统变量和系统变量的值: 系统变量是指系统变量的名称, 通常用在 name属性后面, 不带$, 而在value属性后面需要带value值的时候, 就要使用系统变量的值: 就要加上 $, 即<empty name="Think.post.some_var" value="$Think.get.var2"> ....</else> ...</empty>
  4. 注意所有点模板标签的否定, 都用的是 not, 而不是no, 如notempty, notpresent...
  5. 注意区分: present, defined, empty, define, assign等标签的语义 区别, 和使用的场合:

821299-20170306225400656-680753109.png


如何用find测试 元素中是否包含某个 子元素, 从而来判断用户是否已经登录 ? 

  1. 使用find方法, 但是要注意, find方法是 一个方法, 前面要用 对象, 即范围对象来调用;
  2. find的返回值是一个 jquery 的" 对象", 所以不能用 if来 进行 真假测试!
  3. 821299-20170307001918313-673622948.png
  4. 再次, 证明了 firefox js控制台/调试器的 强大威力. 用来排错js 是非常强大的...

mysql 导出数据库:

821299-20170307102158813-200919118.png


如果客户端没有使用ajax提交, 那么在Controller中即使你调用了ajaxReturn, 也只是返回了数据, 也只是直接显示在当前方法对应的html页面中。
可以使用login, logout或对应的一组: logon, logoff. 而且, login等写在一起的, 通常作为名词,分开写的log in等通常作为动词...

==================================

$.post(url,[data],[callback],[type])

  1. 返回值: XMLHttpRequest 即通常使用的对象变量xhr.
  2. 通过远程 HTTP(get、POST)请求"载入信息", 他的目的只是为了(在页面html已经载入了的情况下,)而不重新刷新/重新载入当前页面的情况下,再次向远程页面请求 载入一些 额外的信息.(通常是和页面中的一些jquery 点击事件相结合使用)。

  3. 最重要的是,js方法中的缺省值跟C/C++等语言中的缺省值,使用方法是不同的, 后者必须按顺序, 缺省值必须在最后。 而js的缺省值,是可以不按顺序的,如果有多个缺省值,前面的缺省值不必/不是必须要 写出来的。

    这是因为,js函数的设计决定的, js函数的参数有不同的表达形式, 根据这些书写形式,就可以判断parse出 是哪个参数了。如图css属性值的设计一样, 根据书写形式就可以判断出是什么属性了.

$.post();

  1. 参数data,始终是一个obj, 总是用{}括起来的, 如果要传递数组,则使用{'arr[]': [1,2,3]} 的形式
    2.注意post和ajax方法的区别, post是直接使用参数, 而ajax是使用的 key:content 的方式
  2. 注意post的回调函数中的data,就是请求载入/远程url返回的内容, 内容的格式根据你指定的格式类型

实际上, jquery对文档dom的处理也是比较简单的.

  1. 在元素内部的增加: append, prepend, appendTo, prependTo
  2. 在元素节点外边的增加(或者说是插入): after,before, insertAfter, insertBefore
  3. 元素的清空和删除: 从语义上也能区别: empty是把元素dom节点清空, 里面没有内容,删除其子节点, 但是元素本身是存在的; 而remove,很明显就是从文档中, 删除这个节点元素了。

如果用jquery来作ajax就非常简单, 省略隐藏包装了很多的细节:

  1. $.ajax()的参数形式, 更简单, 有两种: 一种是 $.ajax(url,[settings]);, 另一种更直接, 就是一个settings, 把url都放入到settings中去了, 即: $.ajax([settings]);
  2. 完整的形式是$.ajax, 但是通常不用这个, 用得最多的还是下面的三个:
  3. 一是load, 载入远程的html代码到当前节点元素: 也就是说, load的调用者,就是远程请求内容以后要插入的地方, load的地址可以是各种形式的:.html,.php,/..,{:U(...)}等都可以,还可以用jquery选择符来选择部分html代码返回.
  4. get和post, 这个就不说了

ajax返回的类型有: xml, html, script, json, text.用得较多的是后面的四种,xml用得比较少:
_ 纯粹的文字,字符串, 用text?

  • 如果是网页格式的, 用html
  • 如果是对象类型的,像key: content 类型的就是json格式
  • 如果是可执行脚本代码的, 用script

load, 如果要传递参数, 默认的方式是Post!

$.ajax, 就使用1个参数, option/settings. 把url也融合进去.
注意区别 : type. dataType, data三个参数的区别, 比较容易混淆...

注意区分ajax的选项参数, 比较接近, 容易混淆
type和datatype:
type是指http 传递的方法, 是get还是post?
dataType: 是指返回的数据类型text, html等等
而data: 则是要传输的数据, 可以使用{key1: val1, key2: val2}的方式, 也可以使用 url地址传值的方式: data:"k1=v1&k2=v2" ,注意这里使用的就是等号不是冒号了!
在写完 url后, 马上就是写这三个类型的值: type, dataType, data.

使用Thinkphp的Verify类来进行验证码

  1. 使用方法是: 先new一个Verify的类对象, 然后调用它的entry方法,就输出了
  2. 整个方法中, 就只有 entry方法是public的, 其他的,像 _background, _writeNoise, _writeCurve等都是private的 , 只是被 entry所调用
  3. 配置参数, 是传递给new 对象时的构造函数的. 在new的时候, 会进行__set, __construct(该函数中, 会汇合 merge($this->config, $config), 其中 $this->config 是类对象 成员protected config 是默认的设置. 当然还有其他的一些设置...如useImgBg, useZh,...
  4. 配置的时候, 可以用 $config数组, 也可以用动态设置 成员变量的方法. 即先new对象, 然后,设置这个对象的成员变量.是因为Verify类中, 有一个公共函数: public function __set($name, $value) 这样就保证了在外部 用 $Verify -> attribute = value的形式时, 调用这个 public的魔法函数.

  5. 注意区别php和C++类在定义成员函数 上的不同, C++虽然也可可以直接在类中声明 并 定义 成员方法, 但是那通常只限于 inline内联方法, 主要的还是,先声明, 然后在类的外部进行实现. 而php的成员方法/函数, 是不用声明, 而且是在 类的内部 直接实现的.

  6. NOW_TIME: 是thinkphp中定义的 时间戳 常量, 表示当前的时间戳....

为什么要使用时间戳? 因为时间戳是秒数, 可以用来进行 时间上的加减 运算, 进行比较, 从而可以 判断 事件是否过期等等, 比如在\Think\Verify中的 check()函数就是用时间戳的比较来判断 验证码是否 过期了的.

获取session中的 验证码: $secode=session[$key]; $secode['verify_time']....


由于使用了mvc, 从而使得"视图"和"控制器"分离, 即html页面和php逻辑分离, 避免了html页面夹杂php代码的情况.

php等支持对象的语言中, 虽然默认的访问权限是public, 但是为了严谨和效率, 应该明确的写出 访问权限是public还是protected private等.不管是成员变量还是成员函数都应该是这样.

注意 Verify::check方法, 返回的是boolean,即验证码是否正确. 而entry方法, 返回的是void, 直接就生成绘制出了 验证码图像.


其实thinkphp的架构还是比较"简单"的, 或者更准确的说, 是:很明晰清楚的:

  • Common, 是包含 functions.php, 主要是一些全局函数.如: C , M , U , A 等函数...
  • Conf, 是包含了系统的配置文件conventions.php, debug.php等..
  • Lang, 语言包, 把常用的, 提示/说明/警告等字符串用变量/配置名称的方式,写出来, 两个作用: 便于修改, 便于在代码中 用变量的方式来引用
  • Library, 库, 这个是tp的核心, 包括: Behavior(切面编程), Org(开源组织写的工具类,如Net, Image等), Think(tp写的), Vendor(其他第三方写的类库)
  • Tpl, 系统的一些 模板, 主要用于跳转, 报错, 异常等页面定制, 如: jump_dispatch.tpl等...

Michigan: [misig2n],密歇根, 密执安州, 湖, 区.
Wisconsin: 威斯康星州, 威斯康辛州.
Philip Katz: 卡兹. zip算法的创始人.
PKzip就是卡兹zip
ARC收费压缩->pkArc->几周后 PKZip ->自由软件打败商业公司的传奇.
PKZIP建立和统治了DOS时代的压缩标准。直到Windows的诞生,使用卡兹创造的压缩算法的软件Winzip的出现更使ZIP格式成为Internet的传输标准,ZIP格式也成为压缩文档的事实标准。
gzip是gnu下的linux的压缩工具.
可以调用imgageCreate(int x_size, int y_size)创建一个空白文件, 然后, 输出imagePng(...), 实际上, 可以直接使用 TP的 Library\Think\Image类来使用php的绘图函数, 它把php的原生函数做了封装..
但是要注意到是: 输出image的时候, 要用header函数做类型声明: Content-type: image/png...否则如果是text/html, 则不会输出图像, 而是输出的图像的二进制编码乱码.

winzip: 比winrar的压缩速度快2倍, 但是不支持rar和iso格式...


php的_ construct 和 initialize 方法?

  1. _ construct是构造函数, 是php类自带的; 而 initialize是 thinkphp框架中的, 只有tp框架才有的,
  2. construct 前面是两个下划线, 而 initialize前面只有一个 下划线
  3. php的类继承, 不像java, c++, 子类会自动调用父类的构造器, php的子类不会自动 调用 父类的construct, 和 initialize.
  4. _initialize实际上就是 调用父类的 parent::__construct
  5. _initialize方法, 会在调用类的每个方法时, 会自动调用 这个_initialize方法.
  6. php的子类可以有自己的构造函数, 如果没有, 不会自动调用父类的构造器, 如果要初始化父类的成员变量, 要显示的调用parent::__construct(父类的参数...). 但是子类没有_initialize, 它会自动调用父类的_initialize函数; 但是如果子类已经有自己的_initialize了, 就不会自动调用父类的初始化函数了, 如果要调用, 则要显式的调用parent::_initaize()
class IndexAction extends BaseAction {

    public function _initialize(){ // 如果子类存在initialize,则不执行父类的内容
        parent::_initialize(); // 加上这一句,才执行父类的初始化函数
        echo "hello I am child";
    }

注意在tp中的跳转, 有success和error, 但是,有时候,不一定 在错误/失败的时候, 就一定要使用 error跳转, 也可以使用 success跳转, 因为success可以指定跳转页面的地址!

但是在用户登录/退出/check/注册等页面, 是不应该执行 权限检查, 是不应该 继承 session()检查, 不应该有_initialize方法的, 因为第一次得要有机会. 就是 将几个额外的方法, 放在另一个类中, 这个类不是继承自 有_initialize方法的类. 而是继承自原始的Controller类. 也就是 , 继承自不同的类... 注意在写tp的Home/Controller中的类的时候, 并不一定所有的类, 都从基类Controller 继承, 有的时候, 可能要写一些 公共类, 公共权限的类, 不需要授权认证的类, 这个时候, 可以直接从Controller继承,如写为: PublicController 或 CommonController, 然后,其他不需要授权的类都从这个CommonController, 而有的类需要认证授权的, 就写一个认证授权的类, 如AuthController, 然后其他类就从这个AuthController的类继承...

在写zen coding / emmet的时候, 它的写法完全就是参考 jquery的 选择器的写法来的, 包括: 标签名,类, id, 属性选择器等, 这里要说的是, 在写inuput这样的表单元素时, 要写表单的类型, 可以直接使用 input:text/password等形式, 而不是采用 [type=text]等的属性样式. 而且 emmet还会给你添加一个 id 和 name在开头和结尾...

<p><input id="" type="text" name=""></p>     // input的属性一般要写的是这三个属性, 而且顺序是: id, type, name, 这三个是有讲究的: 第一个id, 是供前台js用的;
<p><input id="" type="password" name=""></p>    // 最后一个name是供后台 post/get获取表单值用的. 

tp使用验证码的方法是:

  1. 先单独的在类里面, 写一个方法, 生成 验证码 "图片", 如下图所示, 它是一个图片, 而且, 有src地址的png图片
  2. 然后在 想要 "引用" 图片 的地方, 写这个 src 地址, 而不是 在模板页内 用 php标签来 引用验证码, 即: 不是在 引用页, 使用 <php new... entry.../php> 这种方式的
  3. 在tp3.2.3, 中, 生成验证码的方法 跟3.1 不同, 3.1是要 import('ORG.Util.Image'); 然后 调用 Image::buildImageVerify(...), 而3.2.3 , 则直接将Verify这个类, 放在了 TP\Library\Think这个namespace中, 直接就是一个 类: Verify, 通过这个 类的方法 entry来生成 验证码了, 在3.2.3中, 有Library\ORG\Util, 但是已经没有 Image这个类了! 倒是在 \Think下, 有Image这个类, 提供对图片的缩放/水印, 裁剪等操作...

  4. 最重要的是, 要了解 这个 模板 替换常量: _ _URL_ _ 和 _ _APP_ _
    821299-20170321160934158-1505656088.png

关于Behavior行为扩展?

  1. behavior [bi'heivi2]
  2. 从3.2.3, 开始, 引入了 namespace命名空间.
  3. 所有的行为扩展 命名规范(包括你自己写的行为扩展): 文件名是: ???Behavior.class.php, 比如: MyCustBehavior.class.php, 里面的类必须是:
namespace Behavior;
class MyCustBehavior {
 // 所有的行为扩展 的入口执行函数 必须是: 
    public function run (&$foo){

        ....
        // 通常在这里引用, 类的private 函数或 protected 函数....
}

} 
  1. 类的命名方法, 是有两种: 一种是主谓 式, 一种是 动宾式, 如这里的: ContentReplaceBehavior.class.php. 里面的方法是: public function run(&$content){...$this->templateContentReplace($content)...
    821299-20170321164433674-2036125633.png

理解ContentReplaceBehavior中的 $replace = array(....) , 它的实质上, 是一些 URL 地址的 替换! 主要是用来 在 引用/ success/form表单的页面跳转/ 验证码等图像地址引用时的 一些页面地址..

包括了从 根网站 到 当前页面 的地址, 的全部替换:
__ROOT__,
__APP__,
__PUBLIC__,
__MODULE__
__CONTROLLER__  这个controller的URL地址, 就等于 __URL___, 这里记住了, 经常看到的__URL___就是 __CONTROLLER__ 当前控制器所在的 浏览器地址栏的地址URL
__SELF__, 这个self, 是对 __SELF__这个变量做了一次 htmlentities函数处理

因此, 使用得较多的是, __URL__, 当然也可以使用__CONTROLLER__

关于验证码的资源文件, 都是在 \Think\Verify\目录下的, 包括: 中文字体文件夹: zhttfs, 英文字体文件ttfs, 背景图片文件夹: bgs, 默认的验证码使用的是, useNoise => true, useCurve => true, 默认的是使用噪点使用曲线, curve曲线使用的是 正弦曲线, 中文字体使用 zhttfs字体文件才能正常显示!

注意, 3.2.3的验证码字符类型, 默认的就是从 codeSet=>'2345678abc..'中去获取的, 没有0, 1, 9 避免跟字母0, l等相混淆, 所以3.2.3 就没有全是英文字符, 全是数字, 数字和英文字符混合的说法了...自动的就是 从数字和英文字符集中随机抽取.... 如果使用中文, 就要设置, useZh => true, 那么就会自动的从中文字符集中选取: zhSet=...

在所有的js中, 所有的form表单事件函数中, 只要"return false;" (对任意一个input表单控件, 都是可以的), 就表示阻止浏览器的 默认行为..., 如 onpaste ="return false; ondragenter =" return false;"就表示阻止粘贴, 阻止拖放文字... onclick = "submitClick(); return false;就表示阻止默认的提交行为....这种用法具有 通用性...

要阻止在文本框, 密码框等中输入汉字, 只需要 禁用 输入法就好了: style="ime-mode: disabled;"

参考: https://www.lidaren.com/archives/1240 http://www.jb51.net/web/78327.html
但是, 使用ime-mode: disabled; 是 css3 的用法, 有些浏览器是不兼容的, 如windows下的ff, 设置使用了 `style="-moz-ime-mode: disabled;" 都不能禁止输入中文, 因此, 要将样式表和js 结合起来使用:

821299-20170322112740908-926578080.png

转载于:https://www.cnblogs.com/bkylee/p/6497585.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值