Bài 5 — Cảnh báo
- 🇻🇳 Tiếng Việt
- 🇬🇧 English
- 🇰🇷 한국어
- 🇨🇳 中文
Bạn sẽ học: khai báo điều kiện cảnh báo trong script, bật cảnh báo (chạy trên máy chủ FireAnt hoặc trên trình duyệt), chọn tần suất, tránh báo nhầm khi nến chưa đóng, và dùng chính các điều kiện đó để lọc mã.
5.1. Khai báo alerts
alerts là một hàm giống plot, trả về các điều kiện theo tên. Tên là chữ hiện trong hộp đặt cảnh báo và trong thông báo.
indicator({
name: "RSI có cảnh báo",
scale: { range: [0, 100], levels: [30, 70] },
params: {
len: param.int(14, { min: 2, max: 50, label: "Chu kỳ" }),
lo: param.int(30, { min: 5, max: 50, label: "Quá bán" }),
hi: param.int(70, { min: 50, max: 95, label: "Quá mua" }),
},
plot: (d, p) => ({ RSI: line(ta.rsi(d.close, p.len), { color: "accent" }) }),
alerts: (d, p) => {
const r = ta.rsi(d.close, p.len);
return {
"RSI cắt lên quá bán": r.crossAbove(p.lo),
"RSI cắt xuống quá mua": r.crossBelow(p.hi),
};
},
});
Điều kiện cảnh báo không cần vẽ ra; nhưng khi điều kiện cũng hiện thành dấu trên biểu đồ (như Bài 3), bạn thấy ngay trên lịch sử nó sẽ báo ở những nến nào.
5.2. Bật cảnh báo
- Thêm script vào biểu đồ (cảnh báo gắn với script trên biểu đồ này: mã, khung, tham số hiện tại).
- Khung script › ⋯ › Cảnh báo theo script… (hoặc hộp đặt cảnh báo của biểu đồ, loại điều kiện Script).
- Đánh dấu điều kiện muốn nhận, chọn Tần suất, bấm Lưu cảnh báo.
| Tần suất | Báo khi |
|---|---|
| Một lần | Lần đầu điều kiện đúng, rồi tự tắt |
| Mỗi nến một lần (mặc định) | Điều kiện đúng, tối đa một lần cho mỗi nến |
| Mỗi lần tính lại | Mỗi lần giá mới làm điều kiện đúng |
Cảnh báo chạy ở hai nơi:
- Máy chủ FireAnt Thiết yếu (đã đăng nhập): xét cả khi bạn không mở biểu đồ, gửi thông báo qua các kênh của cảnh báo máy chủ. Máy chủ chạy đúng bản script và tham số lúc bạn đặt cảnh báo; hiện chỉ xét ở khung ngày (1D) — Một lần và Mỗi nến một lần xét khi nến ngày đóng, Mỗi lần tính lại xét theo từng giá khớp.
- Trình duyệt (mọi gói): khi biểu đồ đang mở trên FireAnt Terminal, app hiện thông báo ở góc màn hình (và thông báo của trình duyệt nếu bạn đang ở cửa sổ khác).
Chi tiết giao diện: Cảnh báo theo script; cảnh báo máy chủ: Cảnh báo trên biểu đồ.
5.3. Nến đang chạy và báo nhầm
Trong phiên, nến cuối chưa đóng: giá còn đổi nên điều kiện có thể đúng lúc 10:15 rồi sai lúc đóng cửa. Nếu chỉ muốn tín hiệu đã chốt, xét điều kiện của nến vừa đóng bằng shift(1) và chọn tần suất Mỗi nến một lần:
indicator({
name: "Giá cắt MA 20 (nến đã đóng)",
pane: "price",
plot: (d) => ({ "MA 20": line(ta.sma(d.close, 20), { color: "ref" }) }),
alerts: (d) => {
const cat = d.close.crossAbove(ta.sma(d.close, 20));
return {
"Cắt lên MA 20 (đã đóng)": cat.shift(1),
"Cắt lên MA 20 (ngay khi xảy ra)": cat,
};
},
});
cat.shift(1)đúng ở nến sau nến cắt — tức ngay khi nến cắt vừa đóng, và không đổi nữa.- Khai báo dạng đối tượng có thêm tuỳ chọn:
{ when: điều kiện, message: "…", barClose: true }.barClose: trueđánh dấu điều kiện chỉ có nghĩa khi nến đóng: máy chủ cảnh báo luôn xét điều kiện này lúc nến đóng, kể cả khi bạn chọn Mỗi lần tính lại (trong hộp đặt cảnh báo của biểu đồ, chọn Khi nến đóng cho điều kiện này).messagelà lời mô tả điều kiện, lưu cùng khai báo của script; thông báo trên trình duyệt hiện tên điều kiện, mã và giá.
indicator({
name: "Bứt phá đỉnh 20 phiên",
pane: "price",
plot: (d) => ({ "Đỉnh 20 phiên": line(d.high.highest(20).shift(1), { color: "up", dash: "dash", step: true }) }),
alerts: (d) => ({
"Bứt phá": {
when: d.close.crossAbove(d.high.highest(20).shift(1)),
message: "Giá đóng cửa vượt đỉnh 20 phiên",
barClose: true,
},
}),
});
d.high.highest(20).shift(1) là đỉnh của 20 nến trước nến này (không tính nến này — nếu tính, giá không bao giờ "vượt" được chính nó).
5.4. Cảnh báo từ logic theo nến
Khi điều kiện được tính trong onBar (Bài 6), trả nó thành một đầu ra rồi dùng ở alerts qua đối số thứ ba o:
indicator({
name: "5 phiên tăng liên tiếp",
state: () => ({ dem: 0 }),
onBar: (ctx, s) => {
s.dem = ctx.close > ctx.bar(1).close ? s.dem + 1 : 0;
return { dem: s.dem };
},
plot: (d, p, o) => ({ "Số phiên tăng": columns(o.dem, { color: "up" }) }),
alerts: (d, p, o) => ({ "Tăng 5 phiên liền": o.dem.eq(5) }),
});
5.5. Điều kiện cảnh báo cũng để lọc mã
Mỗi điều kiện trong alerts thành một lựa chọn Cảnh báo: … của ⋯ › Lọc bằng script…: chạy điều kiện trên cả VN30, một watchlist hay toàn thị trường để tìm mã vừa có tín hiệu (Bài 12).
Bài tập
Viết chỉ báo cảnh báo khi giá giảm quá 7 % so với đỉnh 20 phiên gần nhất (tính trên giá đóng cửa), báo một lần khi vừa thủng.
Lời giải
indicator({
name: "Giảm 7 % từ đỉnh 20 phiên",
params: { pct: param.pct(0.07, { min: 0.02, max: 0.3, label: "Mức giảm" }) },
plot: (d, p) => {
const tuDinh = d.close.div(d.close.highest(20)).sub(1);
return {
"Từ đỉnh (%)": area(tuDinh.mul(100), { color: "down" }),
"Ngưỡng": line(d.const(-p.pct * 100), { color: "down", dash: "dash" }),
};
},
alerts: (d, p) => ({
"Thủng ngưỡng giảm": d.close.div(d.close.highest(20)).sub(1).crossBelow(-p.pct),
}),
});
param.pct(0.07) cho giá trị tỷ lệ 0,07; ô tham số hiện 7 %. Vì vậy ngưỡng là -p.pct khi so với tỷ lệ, và -p.pct * 100 khi vẽ theo phần trăm.
Tiếp theo: Bài 6 — Tính theo từng nến với onBar
You will learn: how to declare alert conditions in a script, turn alerts on (running on the FireAnt server or in the browser), choose a frequency, avoid false alerts while a candle is still open, and use those same conditions to screen tickers.
5.1. Declaring alerts
alerts is a function like plot that returns conditions by name. The name is the text shown in the set-alert dialog and in notifications.
indicator({
name: "RSI có cảnh báo",
scale: { range: [0, 100], levels: [30, 70] },
params: {
len: param.int(14, { min: 2, max: 50, label: "Chu kỳ" }),
lo: param.int(30, { min: 5, max: 50, label: "Quá bán" }),
hi: param.int(70, { min: 50, max: 95, label: "Quá mua" }),
},
plot: (d, p) => ({ RSI: line(ta.rsi(d.close, p.len), { color: "accent" }) }),
alerts: (d, p) => {
const r = ta.rsi(d.close, p.len);
return {
"RSI cắt lên quá bán": r.crossAbove(p.lo),
"RSI cắt xuống quá mua": r.crossBelow(p.hi),
};
},
});
Alert conditions don't need to be drawn; but when a condition is also shown as a marker on the chart (as in Lesson 3), you can see right away in the history which candles it would alert on.
5.2. Turning alerts on
- Add the script to the chart (the alert is tied to the script on this chart: its current ticker, timeframe and parameters).
- Script pane › ⋯ › Cảnh báo theo script… (Script alerts…) (or the chart's set-alert dialog with the Script condition type).
- Check the conditions you want, choose a Tần suất (Frequency), and click Lưu cảnh báo (Save alert).
| Frequency | Alerts when |
|---|---|
| Một lần (Once) | The condition is true for the first time, then it turns itself off |
| Mỗi nến một lần (Once per candle) (default) | The condition is true, at most once per candle |
| Mỗi lần tính lại (Every recalculation) | Every time a new price makes the condition true |
Alerts run in two places:
- FireAnt server (Essential, signed in): evaluated even when the chart is not open, and notifications are sent through the server alert channels. The server runs exactly the script version and parameters from when you set the alert; it currently evaluates only on the daily timeframe (1D) — Một lần (Once) and Mỗi nến một lần (Once per candle) are evaluated when the daily candle closes, Mỗi lần tính lại (Every recalculation) is evaluated on every matched price.
- Browser (all plans): while the chart is open in FireAnt Terminal, the app shows a notification in the corner of the screen (and a browser notification if you are in another window).
Interface details: Script alerts; server alerts: Alerts on the chart.
5.3. The live candle and false alerts
During a session, the last candle is not yet closed: price is still changing, so a condition can be true at 10:15 and false at the close. If you only want confirmed signals, evaluate the condition on the candle that just closed with shift(1) and choose the Mỗi nến một lần (Once per candle) frequency:
indicator({
name: "Giá cắt MA 20 (nến đã đóng)",
pane: "price",
plot: (d) => ({ "MA 20": line(ta.sma(d.close, 20), { color: "ref" }) }),
alerts: (d) => {
const cat = d.close.crossAbove(ta.sma(d.close, 20));
return {
"Cắt lên MA 20 (đã đóng)": cat.shift(1),
"Cắt lên MA 20 (ngay khi xảy ra)": cat,
};
},
});
cat.shift(1)is true on the candle after the crossing candle — i.e. as soon as the crossing candle has closed, and it no longer changes.- The object form of a declaration adds more options:
{ when: điều kiện, message: "…", barClose: true }(condition, message).barClose: truemarks a condition that only makes sense when the candle closes: the alert server always evaluates it at candle close, even if you chose Mỗi lần tính lại (Every recalculation) (in the chart's set-alert dialog, choose Khi nến đóng (On candle close) for this condition).messageis a description of the condition, stored with the script's declaration; browser notifications show the condition name, ticker and price.
indicator({
name: "Bứt phá đỉnh 20 phiên",
pane: "price",
plot: (d) => ({ "Đỉnh 20 phiên": line(d.high.highest(20).shift(1), { color: "up", dash: "dash", step: true }) }),
alerts: (d) => ({
"Bứt phá": {
when: d.close.crossAbove(d.high.highest(20).shift(1)),
message: "Giá đóng cửa vượt đỉnh 20 phiên",
barClose: true,
},
}),
});
d.high.highest(20).shift(1) is the high of the 20 candles before this one (excluding this candle — if it were included, price could never "break above" itself).
5.4. Alerts from per-candle logic
When a condition is computed in onBar (Lesson 6), return it as an output and use it in alerts through the third argument o:
indicator({
name: "5 phiên tăng liên tiếp",
state: () => ({ dem: 0 }),
onBar: (ctx, s) => {
s.dem = ctx.close > ctx.bar(1).close ? s.dem + 1 : 0;
return { dem: s.dem };
},
plot: (d, p, o) => ({ "Số phiên tăng": columns(o.dem, { color: "up" }) }),
alerts: (d, p, o) => ({ "Tăng 5 phiên liền": o.dem.eq(5) }),
});
5.5. Alert conditions also work for screening
Each condition in alerts becomes a Cảnh báo: … (Alert: …) option in ⋯ › Lọc bằng script… (Screen with script…): run the condition across VN30, a watchlist or the whole market to find tickers with a fresh signal (Lesson 12).
Exercise
Write an indicator that alerts when price falls more than 7% from the high of the latest 20 sessions (based on the close), alerting once when it first breaks below.
Solution
indicator({
name: "Giảm 7 % từ đỉnh 20 phiên",
params: { pct: param.pct(0.07, { min: 0.02, max: 0.3, label: "Mức giảm" }) },
plot: (d, p) => {
const tuDinh = d.close.div(d.close.highest(20)).sub(1);
return {
"Từ đỉnh (%)": area(tuDinh.mul(100), { color: "down" }),
"Ngưỡng": line(d.const(-p.pct * 100), { color: "down", dash: "dash" }),
};
},
alerts: (d, p) => ({
"Thủng ngưỡng giảm": d.close.div(d.close.highest(20)).sub(1).crossBelow(-p.pct),
}),
});
param.pct(0.07) gives the ratio 0.07; the parameter field shows 7%. That is why the threshold is -p.pct when comparing with a ratio, and -p.pct * 100 when drawing in percent.
배울 내용: 스크립트에 알림 조건 선언하기, 알림 켜기(FireAnt 서버 또는 브라우저에서 실행), 빈도 선택, 캔들이 마감되기 전의 잘못된 알림 피하기, 그리고 같은 조건으로 종목 필터링하기.
5.1. alerts 선언
alerts는 plot과 비슷한 함수로, 이름별 조건을 반환합니다. 이름은 알림 설정 대화상자와 알림 메시지에 표시되는 글자입니다.
indicator({
name: "RSI có cảnh báo",
scale: { range: [0, 100], levels: [30, 70] },
params: {
len: param.int(14, { min: 2, max: 50, label: "Chu kỳ" }),
lo: param.int(30, { min: 5, max: 50, label: "Quá bán" }),
hi: param.int(70, { min: 50, max: 95, label: "Quá mua" }),
},
plot: (d, p) => ({ RSI: line(ta.rsi(d.close, p.len), { color: "accent" }) }),
alerts: (d, p) => {
const r = ta.rsi(d.close, p.len);
return {
"RSI cắt lên quá bán": r.crossAbove(p.lo),
"RSI cắt xuống quá mua": r.crossBelow(p.hi),
};
},
});
알림 조건은 그릴 필요가 없습니다. 하지만 조건을 차트에 표시로도 나타내면(3강처럼) 과거 데이터에서 어떤 캔들에 알림이 울릴지 바로 볼 수 있습니다.
5.2. 알림 켜기
- 스크립트를 차트에 추가합니다(알림은 이 차트의 스크립트, 즉 현재 종목, 시간 프레임, 매개변수에 연결됩니다).
- 스크립트 패널 › ⋯ › Cảnh báo theo script…(스크립트 알림…)(또는 차트의 알림 설정 대화상자에서 조건 유형 Script).
- 받을 조건을 체크하고 Tần suất(빈도)를 고른 뒤 Lưu cảnh báo(알림 저장)를 누릅니다.
| 빈도 | 알림 시점 |
|---|---|
| Một lần(한 번) | 조건이 처음 참이 될 때, 이후 자동으로 꺼짐 |
| Mỗi nến một lần(캔들당 한 번)(기본값) | 조건이 참일 때, 캔들당 최대 한 번 |
| Mỗi lần tính lại(재계산할 때마다) | 새 가격으로 조건이 참이 될 때마다 |
알림은 두 곳에서 실행됩니다.
- FireAnt 서버 Essential(로그인 상태): 차트를 열지 않아도 판단하며, 서버 알림 채널로 알림을 보냅니다. 서버는 알림을 설정할 때의 스크립트 버전과 매개변수 그대로 실행합니다. 현재는 **일봉(1D)**에서만 판단합니다. Một lần과 Mỗi nến một lần은 일봉이 마감될 때, Mỗi lần tính lại는 체결가마다 판단합니다.
- 브라우저(모든 플랜): 차트가 FireAnt Terminal에 열려 있을 때 앱이 화면 모서리에 알림을 띄웁니다(다른 창에 있으면 브라우저 알림도 표시).
화면 세부 사항: 스크립트 알림. 서버 알림: 차트 알림.
5.3. 진행 중인 캔들과 잘못된 알림
장중에는 마지막 캔들이 마감되지 않았습 니다. 가격이 계속 바뀌므로 조건이 10:15에는 참이었다가 장 마감 때 거짓이 될 수 있습니다. 확정된 신호만 원하면 shift(1)로 방금 마감된 캔들의 조건을 판단하고, 빈도는 Mỗi nến một lần(캔들당 한 번)을 고르세요.
indicator({
name: "Giá cắt MA 20 (nến đã đóng)",
pane: "price",
plot: (d) => ({ "MA 20": line(ta.sma(d.close, 20), { color: "ref" }) }),
alerts: (d) => {
const cat = d.close.crossAbove(ta.sma(d.close, 20));
return {
"Cắt lên MA 20 (đã đóng)": cat.shift(1),
"Cắt lên MA 20 (ngay khi xảy ra)": cat,
};
},
});
cat.shift(1)은 교차 캔들의 다음 캔들에서 참이 됩니다. 즉 교차 캔들이 막 마감된 순간이며, 이후 더 이상 바뀌지 않습니다.- 객체 형태로 선언하면 옵션이 더 있습니다:
{ when: 조건, message: "…", barClose: true }.barClose: true는 캔들이 마감될 때만 의미가 있는 조건임을 표시합니다. Mỗi lần tính lại(재계산할 때마다)를 골라도 알림 서버는 항상 캔들 마감 시점에 이 조건을 판단합니다(차트의 알림 설정 대화상자에서는 이 조건에 Khi nến đóng(캔들 마감 시)을 고릅니다).message는 조건 설명으로, 스크립트 선언과 함께 저장됩니다. 브라우저 알림에는 조건 이름, 종목, 가격이 표시됩니다.
indicator({
name: "Bứt phá đỉnh 20 phiên",
pane: "price",
plot: (d) => ({ "Đỉnh 20 phiên": line(d.high.highest(20).shift(1), { color: "up", dash: "dash", step: true }) }),
alerts: (d) => ({
"Bứt phá": {
when: d.close.crossAbove(d.high.highest(20).shift(1)),
message: "Giá đóng cửa vượt đỉnh 20 phiên",
barClose: true,
},
}),
});
d.high.highest(20).shift(1)은 이번 캔들 이전 20캔들의 고점입니다(이번 캔들은 포함하지 않음 — 포함하면 가격이 자기 자신을 절대 "넘을" 수 없습니다).
5.4. 캔들별 로직에서 나오는 알림
조건이 onBar에서 계산될 때(6강)는 이를 출력으로 반환한 뒤, 세 번째 인자 o를 통해 alerts에서 사용합니다.
indicator({
name: "5 phiên tăng liên tiếp",
state: () => ({ dem: 0 }),
onBar: (ctx, s) => {
s.dem = ctx.close > ctx.bar(1).close ? s.dem + 1 : 0;
return { dem: s.dem };
},
plot: (d, p, o) => ({ "Số phiên tăng": columns(o.dem, { color: "up" }) }),
alerts: (d, p, o) => ({ "Tăng 5 phiên liền": o.dem.eq(5) }),
});
5.5. 알림 조건으로 종목 필터링도
alerts의 각 조건은 ⋯ › Lọc bằng script…(스크립트로 필터…)의 Cảnh báo: …(알림: …) 선택지가 됩니다. VN30 전체, 관심종목, 또는 시장 전체에서 조건을 실행해 방금 신호가 나온 종목을 찾습니다(12강).
유의 사항
- 스크립트당 조건은 최대 32개입니다.
- 차트에서 숨긴 스크립트는 브라우저가 알림을 판단하지 않습니다.
- 알림을 켠 뒤 첫 계산은 기준점만 잡습니다. 이미 조건을 만족한 과거 캔들에 대해서는 알리지 않습니다.
- 설정 후 코드나 매개변수를 고쳐도 서버에 저장된 알림은 바뀌지 않습니다. 알림 페이지의 Đang đặt(설정된 알림)에서 기존 알림을 지우고 다시 설정하세요.
- Copilot은 알림을 스스로 만들지 않습니다. Cảnh báo theo script(스크립트 알림) 대화상자에서 직접 켜세요.
연습 문제
가격이 최근 20세션 고점 대비 7 % 넘게 하락하면(종가 기준) 알리는 지표를 작성하세요. 막 이탈했을 때 한 번 알립니다.
풀이
indicator({
name: "Giảm 7 % từ đỉnh 20 phiên",
params: { pct: param.pct(0.07, { min: 0.02, max: 0.3, label: "Mức giảm" }) },
plot: (d, p) => {
const tuDinh = d.close.div(d.close.highest(20)).sub(1);
return {
"Từ đỉnh (%)": area(tuDinh.mul(100), { color: "down" }),
"Ngưỡng": line(d.const(-p.pct * 100), { color: "down", dash: "dash" }),
};
},
alerts: (d, p) => ({
"Thủng ngưỡng giảm": d.close.div(d.close.highest(20)).sub(1).crossBelow(-p.pct),
}),
});
param.pct(0.07)은 비율 값 0.07을 주고, 매개 변수 칸에는 7 %로 표시됩니다. 그래서 비율과 비교할 때 기준값은 -p.pct, 퍼센트로 그릴 때는 -p.pct * 100입니다.
您将学到: 在脚本中声明提醒条件,开启提醒(在 FireAnt 服务器或浏览器上运行),选择频率,避免在 K 线未收盘时误报,以及用这些条件来筛选股票代码。
5.1. 声明 alerts
alerts 是一个与 plot 类似的函数,按名称返回各个条件。名称就是显示在设置提醒对话框和通知中的文字。
indicator({
name: "RSI có cảnh báo",
scale: { range: [0, 100], levels: [30, 70] },
params: {
len: param.int(14, { min: 2, max: 50, label: "Chu kỳ" }),
lo: param.int(30, { min: 5, max: 50, label: "Quá bán" }),
hi: param.int(70, { min: 50, max: 95, label: "Quá mua" }),
},
plot: (d, p) => ({ RSI: line(ta.rsi(d.close, p.len), { color: "accent" }) }),
alerts: (d, p) => {
const r = ta.rsi(d.close, p.len);
return {
"RSI cắt lên quá bán": r.crossAbove(p.lo),
"RSI cắt xuống quá mua": r.crossBelow(p.hi),
};
},
});
提醒条件不必绘制出来;但如果条件同时以标记形式显示在图表上(如第 3 课),您就能在历史数据上直接看到它会在哪些 K 线上触发。
5.2. 开启提醒
- 把脚本添加到图表(提醒绑定本图表上的脚本:当前的代码、周期、参数)。
- 脚本窗格 › ⋯ › Cảnh báo theo script…(按脚本提醒…)(或在图表的设置提醒对话框中选择 Script 条件类型)。
- 勾选想接收的条件,选择 Tần suất(频率),点击 Lưu cảnh báo(保存提醒)。
| 频率 | 何时提醒 |
|---|---|
| Một lần(一次) | 条件第一次成立时,之后自动关闭 |
| Mỗi nến một lần(每根 K 线一次,默认) | 条件成立时,每根 K 线最多一次 |
| Mỗi lần tính lại(每次重新计算) | 每次新价格使条件成立时 |
提醒在两个地方运行:
- FireAnt 服务器(Essential,已登录):即使您没有打开图表也会检查,并通过服务器提醒的渠道发送通知。服务器运行的是您设置提醒时那一版脚本和参数;目前只检查日线周期(1D)——Một lần 和 Mỗi nến một lần 在日 K 线收盘时检查,Mỗi lần tính lại 按每笔成交价检查。
- 浏览器(所有套餐):当图表在 FireAnt Terminal 上打开时,应用会在屏幕角落显示通知(如果您在其他窗口,还会显示浏览器通知)。
5.3. 正在形成的 K 线与误报
交易时段内,最后一根 K 线尚未收盘:价格仍在变动,因此条件可能在 10:15 成立,到收盘时却不成立。如果只想要已确认的信号,请用 shift(1) 检查刚收盘那根 K 线的条件,并选择 Mỗi nến một lần(每根 K 线一次)频率:
indicator({
name: "Giá cắt MA 20 (nến đã đóng)",
pane: "price",
plot: (d) => ({ "MA 20": line(ta.sma(d.close, 20), { color: "ref" }) }),
alerts: (d) => {
const cat = d.close.crossAbove(ta.sma(d.close, 20));
return {
"Cắt lên MA 20 (đã đóng)": cat.shift(1),
"Cắt lên MA 20 (ngay khi xảy ra)": cat,
};
},
});
cat.shift(1)在交叉 K 线的下一根 K 线上成立——即交叉 K 线刚收盘之时,并且不会再变。- 对象形式的声明有更多选项:
{ when: điều kiện, message: "…", barClose: true }。barClose: true表示该条件只在 K 线收盘时才有意义:服务器提醒总是在 K 线收盘时检查该条件,即使您选择了 Mỗi lần tính lại(在图表的设置提醒对话框中,为该条件选择 Khi nến đóng,即 K 线收盘时)。message是对条件的描述,与脚本声明一起保存;浏览器通知显示条件名称、代码和价格。
indicator({
name: "Bứt phá đỉnh 20 phiên",
pane: "price",
plot: (d) => ({ "Đỉnh 20 phiên": line(d.high.highest(20).shift(1), { color: "up", dash: "dash", step: true }) }),
alerts: (d) => ({
"Bứt phá": {
when: d.close.crossAbove(d.high.highest(20).shift(1)),
message: "Giá đóng cửa vượt đỉnh 20 phiên",
barClose: true,
},
}),
});
d.high.highest(20).shift(1) 是本根 K 线之前 20 根 K 线的最高点(不含本根——如果包含,价格永远无法“突破”它自己)。
5.4. 来自逐 K 线逻辑的提醒
当条件在 onBar 中计算时(第 6 课),把它作为一个输出返回,再通过第三个参数 o 在 alerts 中使用:
indicator({
name: "5 phiên tăng liên tiếp",
state: () => ({ dem: 0 }),
onBar: (ctx, s) => {
s.dem = ctx.close > ctx.bar(1).close ? s.dem + 1 : 0;
return { dem: s.dem };
},
plot: (d, p, o) => ({ "Số phiên tăng": columns(o.dem, { color: "up" }) }),
alerts: (d, p, o) => ({ "Tăng 5 phiên liền": o.dem.eq(5) }),
});
5.5. 提醒条件也可用于选股
alerts 中的每个条件都会成为 ⋯ › Lọc bằng script…(用脚本筛选…)中的一个 Cảnh báo: …(提醒:…)选项:在整个 VN30、某个自选股列表或全市场上运行该条件,找出刚出现信号的代码(第 12 课)。
练习
编写一个指标,当价格较最近 20 个交易时段的高点下跌超过 7% 时提醒(按收盘价计算),刚跌破时提醒一次。
答案
indicator({
name: "Giảm 7 % từ đỉnh 20 phiên",
params: { pct: param.pct(0.07, { min: 0.02, max: 0.3, label: "Mức giảm" }) },
plot: (d, p) => {
const tuDinh = d.close.div(d.close.highest(20)).sub(1);
return {
"Từ đỉnh (%)": area(tuDinh.mul(100), { color: "down" }),
"Ngưỡng": line(d.const(-p.pct * 100), { color: "down", dash: "dash" }),
};
},
alerts: (d, p) => ({
"Thủng ngưỡng giảm": d.close.div(d.close.highest(20)).sub(1).crossBelow(-p.pct),
}),
});
param.pct(0.07) 给出比率值 0.07;参数框显示 7%。因此与比率比较时阈值为 -p.pct,按百分比绘制时为 -p.pct * 100。