ちょいネタ。
このスクリプトをから作成できる実行ファイルを既存のhelpman.exeと置き換えることで、Online HSP Document Libraryをワンキーヘルプとして利用できます。
実行ファイルの作成はctrl+F9の「実行ファイル自動作成」を利用してください。#packopt name "helpman"
#packopt hide 1
    exec "http://www.onionsoft.net/hsp/ref/ohdl.cgi?cmd=hdsrch&arg="+dir_cmdline, 16
    end
2008年6月7日土曜日
Online HSP Document Libraryをワンキーヘルプとして使う
2008年5月17日土曜日
自力型変換(int⇔str)
整数値と文字列を相互に変換します。HSPでは特に気にせず利用できる機能ですが、自力でやると結構面白いものです。
数値の桁数を計算するためにHSPMathのlog10関数を使用。おまけとしてTrim関数がついてます。
2008.05.17 memcpyをなくすことで計量化// 自力で型変換
//     2008.05.17 計量化
#module
#include "hspmath.as"
// 文字列の始めと終わりにある半角スペースを除去
#defcfunc Trim str s, local target, local target_length, local result
    target = s
    target_length = strlen( target )
    repeat target_length
        start_idx = cnt
        if peek( target, start_idx ) != ' ' : break
    loop
    repeat target_length, 1
        end_idx = target_length - cnt
        if peek( target, end_idx ) != ' ' : break
    loop
    result = strmid( target, start_idx, end_idx + 1 - start_idx )
    return result
#define ctype not_digit(%1) ((%1) < '0' | '9' < (%1))
// 文字列を整数値に変換
#defcfunc str2int str s, local target, local result, local target_length
    result = 0
    target = Trim( s )
    if peek( target ) = '-' : sign = -1 : else : sign = 1
    if peek( target ) = '-' | peek( target ) = '+' {
        target = strmid( target, 1, strlen( target ) - 1 )
    }
    target_length = strlen( target )
    for i, iStart, target_length
        if not_digit( peek( target, i ) ) : _break
        result = result * 10 + peek( target, i ) - '0'
    next
    return result * sign
// 整数値を文字列に変換
#defcfunc int2str int p, local target, local result, local result_length
    if p = 0 : return "0"
    target = abs( p )
    result_length = 1 + log10( target ) + ( p < 0 )
    sdim result, result_length + 1
    repeat 1 + log10( target ), 1
        poke result, result_length - cnt, ( target \ 10 ) + '0'
        target /= 10
    loop
    if p < 0 {
        poke result, 0, '-'
    }
    return result
#global
2008年4月19日土曜日
花火ゲーム(やわらかライセンス)
 ( ゜ワ゜)ノさん原案、eller改造のミニゲーム。
( ゜ワ゜)ノさん原案、eller改造のミニゲーム。
このスクリプトはやわらかライセンスのもとで、自由に改造・配布が可能です。/* HANABIGA @ やわらかライセンス by eller 2008/04/19
 * ===============================================
 * SAKURAGAからの改造個所:
 *     "さくら" → "たまや"       // "かぎや"でも良い
 *     キャラクタの移動動作変更(ちょい簡単に)
 *     背景色など色合い変更
 *     ゲームオーバー中はキャラクタを生成しないように
 *     キャラクタ接触時にどかーん
 *     ゲームオーバー時にどかーん
 *     redraw 0 と redraw 1 を入れ替え
 *     randomize追加
 *     640 → ginfo_winx など
 */
//#runtime "hsplet3"
#include "hspmath.as"
#packopt name "hanabiga"
#define FRAME_WAIT          16
#define PLAYER_SPEED        3.0
#define PLAYER_SP_REDUCE    0.8
#define CHAR_MAX            256
#define HANABI_MAX          8
#define CHAR_TYPE_NONE      0
#define CHAR_TYPE_SA        1
#define CHAR_TYPE_KU        2
#define CHAR_TYPE_RA        3
#define CHAR_FACE_SA        "た"
#define CHAR_FACE_KU        "ま"
#define CHAR_FACE_RA        "や"
#define CHAR_FACE_HANABI    "・"
#define HANABI_PARTS_NUM    14
#define CHAR_ROT_SP         0.05
#define CHAR_ROT_MOVE       0.8
#define CHAR_SIZE           16.0
// 準備
;   screen 0, 480, 320
    title "SAKURAGA 2008"
    font "MS ゴシック" ,16,1
    randomize
    player_x = double(ginfo_winx / 2)
    player_y = double(ginfo_winy / 2)
    player_vx = 0.0
    player_vy = 0.0
    dim char_type,CHAR_MAX
    ddim char_x,CHAR_MAX
    ddim char_y,CHAR_MAX
    ddim char_vx,CHAR_MAX
    ddim char_vy,CHAR_MAX
    dim char_timer,CHAR_MAX
    ddim hanabi_x,HANABI_MAX
    ddim hanabi_y,HANABI_MAX
    dim hanabi_radius,HANABI_MAX
    dim hanabi_life,HANABI_MAX
    dim hanabi_life_max,HANABI_MAX
    dim hanabi_r,HANABI_MAX
    dim hanabi_g,HANABI_MAX
    dim hanabi_b,HANABI_MAX
    buffer 1,640,480
    repeat 40
        color cnt, 0, cnt * 2
        boxf 0 , cnt * ginfo_winy / 40 , ginfo_winx , (cnt + 1) * ginfo_winy / 40
    loop
    gsel 0
    gmode 3,,,64
// メイン処理
repeat
    // INIT
    gosub *initpl
    // タイトル
    repeat
        redraw 0
        gosub *clearscreen
        gosub *movehanabi
        gosub *movechar
        gosub *collision
        if(player_life > 0){
            gosub *moveplayer
            a = 10 - (player_score / 5) \ 10
            if( a < 2 ) : a = 1
            if(player_timer \ a  == 0) : gosub *addchar
        }else{
            gosub *burstall
            color 255, 255, 255
            pos (ginfo_winx - 198)/ 2, (ginfo_winy - 16) / 2
            mes "H A N A B I  O W A T A"
            stick inp
            if(inp & 16) : break
        }
        gosub *showstatus
        redraw 1
        await FRAME_WAIT
    loop
loop
*initpl
    player_x = double(ginfo_winx / 2)
    player_y = double(ginfo_winy / 2)
    player_vx = 0.0
    player_vy = 0.0
    player_life = 1
    player_chain_type = CHAR_TYPE_SA
    player_score = 0
    scroll_vx = 0.01
    scroll_vy = -2.0
    repeat CHAR_MAX
        char_type(cnt) = CHAR_TYPE_NONE
    loop
    return
*clearscreen
    pos 0,0
    gcopy 1,0,0,ginfo_winx, ginfo_winy
    return
*moveplayer
    stick inp,255
    if(inp & 1) : player_vx -= PLAYER_SPEED
    if(inp & 2) : player_vy -= PLAYER_SPEED
    if(inp & 4) : player_vx += PLAYER_SPEED
    if(inp & 8) : player_vy += PLAYER_SPEED
    player_timer++
    player_vx *= PLAYER_SP_REDUCE
    player_vy *= PLAYER_SP_REDUCE
    player_x = limitf(player_x + player_vx, 0.0, ginfo_winx - CHAR_SIZE)
    player_y = limitf(player_y + player_vy, 0.0, ginfo_winy - CHAR_SIZE)
    
    color 255
    pos player_x,player_y
    if( player_chain_type == CHAR_TYPE_SA ){
        mes CHAR_FACE_SA
    } else : if( player_chain_type == CHAR_TYPE_KU ){
        mes CHAR_FACE_KU
    } else : if( player_chain_type == CHAR_TYPE_RA ){
        mes CHAR_FACE_RA
    }
    return
*collision
    repeat CHAR_MAX
        if( char_type(cnt) == CHAR_TYPE_NONE ) : continue
        dx = player_x - char_x(cnt)
        dy = player_y - char_y(cnt)
        if( abs(dx) < CHAR_SIZE & abs(dy) < CHAR_SIZE ) {
            if( char_type(cnt) == player_chain_type ){
                player_chain_type++
                if(player_chain_type > CHAR_TYPE_RA){
                    player_chain_type = CHAR_TYPE_SA
                }
                player_score++
            }else{
                player_life--
            }
            char_type(cnt) == CHAR_TYPE_NONE
            x = char_x(cnt)
            y = char_y(cnt)
            gosub *addhanabi
        }
    loop
    return
*movechar
    color 255,128
    repeat CHAR_MAX
        if( char_type(cnt) == CHAR_TYPE_NONE ) : continue
        pos char_x(cnt) , char_y(cnt) 
        char_x(cnt) += char_vx(cnt)
        char_y(cnt) += char_vy(cnt)
        char_timer(cnt)++
        char_x(cnt) += CHAR_ROT_MOVE * sin(double(CHAR_ROT_SP * char_timer(cnt)))
        char_y(cnt) += CHAR_ROT_MOVE ;* cos(double(CHAR_ROT_SP * char_timer(cnt)))
        if( char_y(cnt) < -16.0 ) : char_type(cnt) = CHAR_TYPE_NONE
        if( char_type(cnt) == CHAR_TYPE_SA ){
            mes CHAR_FACE_SA
        } else : if( char_type(cnt) == CHAR_TYPE_KU ){
            mes CHAR_FACE_KU
        } else : if( char_type(cnt) == CHAR_TYPE_RA ){
            mes CHAR_FACE_RA
        }
    loop
    return
*addchar
    repeat CHAR_MAX
        if( char_type(cnt) != CHAR_TYPE_NONE ) : continue
        char_type(cnt) = 1 + rnd(3)
        char_x(cnt) = double(rnd(800) - 80)
        char_y(cnt) = 20.0 + ginfo_winy
        char_vx(cnt) = scroll_vx
        char_vy(cnt) = scroll_vy
        char_timer(cnt) = rnd(256)
        break
    loop
    return
*showstatus
    pos ginfo_winx - 120 , ginfo_winy - 20
    color 255, 255, 255
    mes "SCORE : " + player_score
    
    return
#const HANABI_CST 2.0 * M_PI / HANABI_PARTS_NUM
*movehanabi
    repeat HANABI_MAX
        if( hanabi_life(cnt) <= 0 ) : continue
        hanabi_life(cnt)--
        color hanabi_r(cnt), hanabi_g(cnt), hanabi_b(cnt)
        ; hanabi_y(up_cnt)++
        up_cnt = cnt
        r = cos(M_PI * hanabi_life(cnt) / hanabi_life_max(cnt) / 2.0) * hanabi_radius(cnt)
        repeat HANABI_PARTS_NUM
            pos hanabi_x(up_cnt) + cos(HANABI_CST * cnt) * r, hanabi_y(up_cnt) + sin(HANABI_CST * cnt) * r
            mes CHAR_FACE_HANABI
        loop
    loop
    return
*addhanabi
    result = 0
    repeat HANABI_MAX
        if( hanabi_life(cnt) > 0 ) : continue
        hanabi_x(cnt) = x
        hanabi_y(cnt) = y
        size = 10 + rnd(12)
        hanabi_life_max(cnt) = size
        hanabi_life(cnt)     = size
        hanabi_radius(cnt)   = size * 3
        hsvcolor rnd(192), 255, 255
        hanabi_r(cnt) = ginfo_r
        hanabi_g(cnt) = ginfo_g
        hanabi_b(cnt) = ginfo_b
        result = 1
        break
    loop
    return result
*burstall
    repeat CHAR_MAX
        if( char_type(cnt) = CHAR_TYPE_NONE ) : continue
        x = char_x(cnt)
        y = char_y(cnt)
        gosub *addhanabi
        if stat : char_type(cnt) = CHAR_TYPE_NONE
    loop
    return
2008年3月29日土曜日
文字列のセンタリング
どう書く?orgより。
文字列の長さに応じて、ifで分岐しています。もっとスマートに記述できないものでしょうか?/*
    どう書く?org より
        文字列のセンタリング
        http://ja.doukaku.org/87/
*/
#runtime "hsp3cl"
#module
#defcfunc spaces int len
    if len <= 0 : return ""
    sdim s, len + 1
    repeat len
        poke s, cnt, ' '
    loop
    return s
#defcfunc centered_text str target, int len
    if len <= 0 : return ""
    target_length = strlen(target)
    result = target
    if target_length < len {
        result = spaces((len - target_length)/2) + target + spaces((len - target_length + 1)/2)
    } else : if target_length > len {
        result = strmid(result, (target_length - len)/2, len)
    }
    return result
#global
    s = "*"
    repeat 10
        mes centered_text(s, 15)
        s += " *"
    loop
    stop
追記。
ifによる条件分岐をlimit関数に置き換えました。/*
    どう書く?org より
        文字列のセンタリング
        http://ja.doukaku.org/87/
*/
#runtime "hsp3cl"
#module
#defcfunc centered_text str _source, int len
    if len <= 0 : return ""
    source = _source
    source_strlen = strlen(source)
    sdim result, len + 1
    memset result, ' ', len
    poke result, limit((len - source_strlen)/2, 0, len/2), strmid(source, limit((source_strlen - len)/2, 0, source_strlen), len)
    return result
#global
    s = "*"
    repeat 10
        mes centered_text(s, 15)
        s += " *"
    loop
    stop
2008年3月18日火曜日
HSP入門者向け講座リンク集 更新
クロノス・クラウンにてHSP入門者向け講座リンク集が更新されました。HSP関連サイトを横断的に検索できるサービスも追加されています。
なお、当ブログは難易度中~高と評価されています。
関連
2008年3月6日木曜日
2008年3月1日土曜日
日数計算・曜日計算
 COMを利用した、日付を扱うモジュールです。
COMを利用した、日付を扱うモジュールです。
指定した日の曜日を算出する関数と、指定した2つの日の差(日数)を算出する関数を含んでいます。
日数算出は「あと何日あるか」を算出するので、このサンプルプログラムのように「全部で何日か」を計算する場合は1を足す必要があります。/*
    日付を扱うライブラリになりそうなもの。
    ※ 注意!パラメータチェック&エラーチェック処理未実装!
    参考:http://tsu.sakura.ne.jp/article/note/eid512.html
*/
#module
// ミリ秒を日に変換
#define ctype cnvMsec2Day(%1) int((%1)/86400000)  // 86400000 = 1000*60*60*24
// javascript数式の計算
#defcfunc jsEval str jsExp
    if vartype(mssc) != vartype("comobj") {
        newcom mssc, "MSScriptControl.ScriptControl"
        comres result
        mssc("Language") = "JScript"
    }
    mssc -> "Eval" jsExp
    return result
// 曜日を返す(0~6)
#defcfunc getDayOf int y, int m, int d
    return int(jsEval("(new Date(" + y + "," + (m - 1) + "," + d + ")).getDay();"))
// 時間差を日数で返す
#defcfunc getSub int y1, int m1, int d1, int y2, int m2, int d2
    return cnvMsec2Day(jsEval("Date.UTC(" + y2 + "," + (m2 - 1) + "," + d2 + ") - Date.UTC(" + y1 + "," + (m1 - 1) + "," + d1 + ");"))
#global
// モジュールここまで
    day = "日", "月", "火", "水", "木", "金", "土"
    mes "今年は" + (1 + getSub( gettime(0), 1, 1, gettime(0), 12, 31 )) + "日間です"
    mes "今日は" + day( getDayOf( gettime(0), gettime(1), gettime(3) ) ) + "曜日です"
    stop
2008年2月12日火曜日
アンドゥや再生ができるペイントツール
GoFのCommandパターンにヒントを得て作成。
描画した履歴を文字列型配列変数に記録しておき、必要に応じて取り出します。
今回は単純な文字列型配列変数ではなく、スタックのモジュールを用意してみました。
bregexp.dll(bregonig.dll)および月影ともさんのbregexp.hspが必要です。// 文字列用スタック
#module string_stack stack, max
#modinit
    max = 0
    sdim stack, 32, 10
    return
#deffunc new_sstack array v
    newmod v, string_stack@
    return
#modfunc push str s
    stack(max) = s
    max++
    return
#defcfunc pop modvar string_stack@
    if max == 0 {
        logmes "引数の値が異常です。"
        return ""
    }
    max--
    return stack(max)
#defcfunc get_length modvar string_stack@
    return max
#defcfunc get_last modvar string_stack@
    return stack(max-1)
#defcfunc get_at modvar string_stack@, int index
    if index < 0 || max <= index {
        logmes "引数の値が異常です。"
        return ""
    }
    return stack(index)
#modfunc clear_stack
    max = 0
    return
#global
// 矩形の塗りつぶし
// http://rpen.blogspot.com/2007/11/blog-post.html
#include "gdi32.as"
#module
#const FLOODFILLSURFACE 1
#deffunc fill int x, int y
    current_color = ginfo_r, ginfo_g, ginfo_b
    CreateSolidBrush (ginfo_b << 16) | (ginfo_g << 8) | ginfo_r
    if stat {
        hBrush = stat
    } else {
        dialog "ブラシの生成に失敗しました。プログラムを終了します。", 1
        end
    }
    SelectObject hDC, hBrush
    pget x, y
    ExtFloodFill hdc, x, y, (ginfo_b << 16) | (ginfo_g << 8) | ginfo_r, FLOODFILLSURFACE
    DeleteObject hBrush
    color current_color(0), current_color(1), current_color(2)
    return
#global
// 命令を解析して描画するモジュール
#include "bregexp.hsp"
#module drawer
#define ctype result(%1) int(_result(%1))
#deffunc draw str _cmd
    cmd = _cmd
    BSplit _result, cmd, "m/[ ,]+/"
    switch _result(0)
        case "moveTo" : pos result(1), result(2) : swbreak
        case "lineTo" : line result(1), result(2) : swbreak
        case "color"  : color result(1), result(2), result(3) : swbreak
        case "fill"   : fill result(1), result(2) : redraw 1 : swbreak
        default : logmes "未知の命令です" : swbreak
    swend
    return
#deffunc draw_all array cmds, int wait_time
    redraw 0
    color 255, 255, 255 : boxf
    color
    repeat get_length(cmds)
        draw get_at(cmds, cnt)
        if wait_time {
            redraw 1
            wait wait_time
            redraw 0
        }
    loop
    redraw 1
    return
#global
#define push_and_do(%1,%2) push %1, %2 : draw %2
#define WM_MOUSEMOVE    $00000200
#define WM_LBUTTONDOWN  $00000201
#define WM_LBUTTONUP    $00000202
#define WM_RBUTTONDOWN  $00000204
*init
    title "左ドラッグで線を描画 / 右クリックで塗りつぶし"
    oncmd gosub *onLButtonDown, WM_LBUTTONDOWN
    oncmd gosub *onRButtonDown, WM_RBUTTONDOWN
    oncmd gosub *onLButtonUp, WM_LBUTTONUP
    oncmd gosub *onMouseMove, WM_MOUSEMOVE
    objsize 80
    button gosub "color change", *color_change
    button gosub "redraw slowly", *all_draw_slowly
    button gosub "clear", *clear
    button gosub "undo", *undo
    new_sstack cmds
    stop
// 色の変更
*color_change
    hsvcolor rnd(192), 255, 255
    push_and_do cmds, "color " + ginfo_r + "," + ginfo_g + "," + ginfo_b
    return
// 全消去
*clear
    clear_stack cmds
    draw_all cmds, 0
    return
// アンドゥ
*undo
    tmp = pop(cmds)
    draw_all cmds, 0
    return
// すべて描画
*all_draw
    draw_all cmds, 0
    return
// ゆっくりとすべて描画
*all_draw_slowly
    oncmd 0
    gosub *invalidate_buttons
    draw_all cmds, 4
    gosub *validate_buttons
    oncmd 1
    return
// 左ドラッグ開始
*onLButtonDown
    dragging = 1
    push_and_do cmds, "moveTo " + mousex + "," + mousey
    return
// 左ドラッグ終了
*onLButtonUp
    dragging = 0
    return
// 左ドラッグ中
*onMouseMove
    if dragging {
        push_and_do cmds, "lineTo " + mousex + "," + mousey
    }
    return
// 右クリック
*onRButtonDown
    if dragging == 0 {
        push_and_do cmds, "fill " + mousex + "," + mousey
    }
    return
#include "obj.as"
*invalidate_buttons
    repeat 4
        objgray cnt, 0
    loop
    return
*validate_buttons
    repeat 4
        objgray cnt, 1
    loop
    return
2008年2月9日土曜日
リストビューのソート
 リストビューのアイテムをLVM_SORTITEMSEXメッセージを使ってソートします。ちょくとさんのコールバック関数DLL「hscallbk.dll」が必要です。
リストビューのアイテムをLVM_SORTITEMSEXメッセージを使ってソートします。ちょくとさんのコールバック関数DLL「hscallbk.dll」が必要です。
リストビューのモジュールとしてもそこそこ利用できるかもしれません。
エクスプローラのように、「ヘッダ部分をクリックすると並び変わる」ようにもできるでしょう。(参考:http://hsp.tv/play/pforum.php?mode=pastwch&num=2749)
LVM_SORTITEMSEXメッセージの日本語情報は意外と少ないので、気が向いたら開発Wikiにフィードバックします。// 参考資料:
//      リストビューを作成してみる
//          http://yokohama.cool.ne.jp/chokuto/urawaza/listview1.html
//      Windows32 API Constance 検索
//          http://hspnext.com/tool/hsptool04.htm
//      MSDN - LVM_SORTITEMSEX
//          http://msdn2.microsoft.com/ja-jp/library/bb761055(en-us).aspx
#module mod_listview
#include "hscallbk.as"
#uselib ""
#func sort_items "" int, int, int
#define LVM_SETITEM             $00001006
#define LVM_INSERTITEM          $00001007
#define LVM_INSERTCOLUMN        $0000101B
#define LVM_SORTITEMSEX         $00001051
#define LVM_GETITEMTEXTA        $0000102D
#define LVS_REPORT              $00000001
#define WS_EX_NOPARENTNOTIFY    $00000004
#define WS_VISIBLE              $10000000
#define WS_CHILD                $40000000
#deffunc make_listview
    if vartype(proc) != vartype("callback") : gosub *init
    winobj "SysListView32", "ListView", WS_EX_NOPARENTNOTIFY, WS_VISIBLE | WS_CHILD | LVS_REPORT, -1, -1
    return stat
*init
    setcallbk proc, sort_items, *sort_flag
    sdim name, 64, 2
    dim lvcolumn, 8
    dim lvitem, 6
    lvcolumn.0 = 0x000F
    lvcolumn.2 = 100
    lvitem.0 = 0x0001
    lvitem.6 = 64
    return
#deffunc add_column int id_list, str column_name, int index
    if(index < 0 | id_list < 0) {
        logmes "パラメータが不正です。"
        return -1
    }
    name = column_name
    lvcolumn.3 = varptr(name)
    sendmsg objinfo_hwnd(id_list), LVM_INSERTCOLUMN, index, varptr(lvcolumn)
    return stat
#deffunc add_item int id_list, array item, int index
    if(index < 0 | id_list < 0) {
        logmes "パラメータが不正です。"
        return -1
    }
    if vartype(item) != vartype("str") {
        logmes "配列変数の型が不正です。文字列型の変数を渡してください。"
        return -1
    }
    // アイテムの作成
    lvitem.1 = index
    lvitem.2 = 0
    lvitem.5 = varptr(item)
    sendmsg objinfo_hwnd(id_list), LVM_INSERTITEM, 0, varptr(lvitem)
    // サブアイテムの作成
    repeat length(item) - 1, 1
        lvitem.2 = cnt
        lvitem.5 = varptr(item(cnt))
        sendmsg objinfo_hwnd(id_list), LVM_SETITEM, 0, varptr(lvitem)
    loop
    return stat
#deffunc sort int id_list, int column, int vtype, int sortmode
    if(column < 0 | id_list < 0 | vtype < 0) {
        logmes "パラメータが不正です。"
        return -1
    }
    lvitem.2 = column
    var_type = vtype
    sendmsg objinfo_hwnd(id_list), LVM_SORTITEMSEX, sortmode, varptr(proc)
    return
#defcfunc local compareAsInt int id_list, int index1, int index2, int sortmode
    gosub *startCompare
    return int(name(sortmode & 1)) - int(name((sortmode & 1) ^ 1))
#defcfunc local compareAsStr int id_list, int index1, int index2, int sortmode
    gosub *startCompare
    return name(sortmode & 1) ! name((sortmode & 1) ^ 1)
    return
*startCompare
    lvitem.5 = varptr(name(0))
    sendmsg objinfo_hwnd(id_list), LVM_GETITEMTEXTA, index1, varptr(lvitem)
    lvitem.5 = varptr(name(1))
    sendmsg objinfo_hwnd(id_list), LVM_GETITEMTEXTA, index2, varptr(lvitem)
    return
// サブアイテム(ファイルサイズ)でソート
// 第3引数が0なら昇順、1なら降順
*sort_flag
    if var_type == vartype("int") {
        return compareAsInt@mod_listview(id_list, callbkarg(0), callbkarg(1), callbkarg(2))
    } else : if var_type == vartype("str") {
        return compareAsStr@mod_listview(id_list, callbkarg(0), callbkarg(1), callbkarg(2))
    }
    return 0
#global // end of mod_listview
// 疑似的な「ファイル」の数
#define NUM_FILES   10
    randomize
    gosub *createGuiObjects
    stop
// ボタンクリックによって呼び出されるサブルーチン
*sort_asc_by_name
    sort id_list, 0, vartype("str"), 0
    return
*sort_desc_by_name
    sort id_list, 0, vartype("str"), 1
    return
*sort_asc_by_size
    sort id_list, 1, vartype("int"), 0
    return
*sort_desc_by_size
    sort id_list, 1, vartype("int"), 1
    return
// ボタンとリストビューの作成
*createGuiObjects
    // ボタンを作成
    objsize ginfo_winx / 4, 32
    pos 0, 0 : button gosub "ファイル名で昇順にソート", *sort_asc_by_name
    pos ginfo_winx / 4, 0 : button gosub "ファイル名で降順にソート", *sort_desc_by_name
    pos ginfo_winx / 2, 0 : button gosub "ファイルサイズで昇順にソート", *sort_asc_by_size
    pos ginfo_winx * 3 / 4, 0 : button gosub "ファイルサイズで降順にソート", *sort_desc_by_size
    // リストビューコントロール作成
    pos 0, 32 : objsize ginfo_winx, ginfo_winy - 32
    make_listview : id_list = stat
    // カラムを追加
    column_name = "ファイル名", "ファイルサイズ"
    repeat 2
        add_column id_list, column_name(cnt), cnt
        if stat == -1 {
            dialog "カラムの追加に失敗", 1
            end
        }
    loop
    // アイテム・サブアイテムの追加
    sdim item_name, 64, 2
    repeat NUM_FILES
        item_name = "ファイル" + cnt, "" + rnd(1000) + " KB"
        add_item id_list, item_name, cnt
        if stat == -1 {
            dialog "アイテムの追加に失敗", 1
            end
        }
    loop
    return
2008年2月5日火曜日
正規表現でHTMLの見出しを抽出する
 bregonig.dllを使いたくて「ヘッダファイル作ろうかなー」と考えていたら既に月影ともさん(と猫太さん)が作成されていました。
bregonig.dllを使いたくて「ヘッダファイル作ろうかなー」と考えていたら既に月影ともさん(と猫太さん)が作成されていました。
COMによる正規表現は何かと不便なので、今後重宝しそうです。
リンク先を変更。[08/05/03]// つーさのくーかん「物置 > HSP3 > BREGEXP.hsp」
// http://tu-sa.net/0360
#runtime "hsp3cl"
#include "bregexp.hsp"
    dialog "htm;*.html", 16, "見出しを抽出するHTMLファイル"
    if stat == 0 : end
    notesel file
    noteload refstr
    position = 0
    margin_left = "-", "--", "---", "----", "-----", "------"
    repeat
        result = BMatch(file, position, "m#<[hH]([1-6])[^>]*>(.*)</[hH]\\1>#k")
        if result == -1 : break
        mes margin_left(int(BMGetStr(1))-1) + BMGetStr(2)
        position += BMGetNextPos()
    loop
    stop
 

