Skip to content

Commit 4b5dfaf

Browse files
authored
feat: iterators (#5)
1 parent 96c385a commit 4b5dfaf

File tree

2 files changed

+114
-6
lines changed

2 files changed

+114
-6
lines changed

src/glitzer.gleam

+34-4
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
import gleam/int
2+
import gleam/iterator
3+
14
import glitzer/progress
25

36
@external(erlang, "glitzer_ffi", "sleep")
@@ -10,19 +13,46 @@ pub fn main() {
1013
|> progress.with_length(10)
1114

1215
do_something(bar, 0)
16+
do_something_else()
17+
do_cool_shit_with_2_it()
1318
}
1419

1520
fn do_something(bar, count) {
1621
case count < 10 {
1722
True -> {
18-
let bar = case count > 5 {
19-
True -> progress.finish(bar)
20-
False -> progress.tick(bar)
21-
}
23+
let bar = progress.tick(bar)
2224
progress.print_bar(bar)
2325
sleep(100)
2426
do_something(bar, count + 1)
2527
}
2628
False -> Nil
2729
}
2830
}
31+
32+
fn do_something_else() {
33+
let bar =
34+
progress.fancy_slim_arrow_bar()
35+
|> progress.with_length(10)
36+
37+
iterator.range(0, 10)
38+
|> progress.each_iterator(bar, fn(bar, i) {
39+
progress.with_left_text(bar, int.to_string(i) <> " ")
40+
|> progress.print_bar
41+
sleep(100)
42+
})
43+
}
44+
45+
fn do_cool_shit_with_2_it() {
46+
let bar =
47+
progress.default_bar()
48+
|> progress.with_length(10)
49+
let i1 = iterator.range(0, 10)
50+
let i2 = iterator.range(100, 150)
51+
progress.map2_iterator(i1, i2, bar, fn(bar, e1, e2) {
52+
progress.with_left_text(bar, int.to_string(e1) <> " ")
53+
|> progress.with_right_text(" " <> int.to_string(e2))
54+
|> progress.print_bar
55+
sleep(100)
56+
})
57+
|> iterator.run
58+
}

src/glitzer/progress.gleam

+80-2
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import gleam/io
2+
import gleam/iterator.{type Iterator}
23
import gleam/option.{type Option}
34
import gleam/string
45
import gleam/string_builder.{type StringBuilder}
@@ -281,17 +282,28 @@ pub fn finish(bar bar: ProgressStyle) -> ProgressStyle {
281282
/// }
282283
/// ```
283284
pub fn print_bar(bar bar: ProgressStyle) {
285+
let bar =
286+
ProgressStyle(
287+
..bar,
288+
state: State(..bar.state, finished: bar.state.progress >= bar.length),
289+
)
284290
let fill =
285-
build_progress_fill(string_builder.new(), bar, bar.state.progress, 0)
291+
build_progress_fill(string_builder.new(), bar, bar.state.progress + 1, 0)
286292
|> string_builder.to_string
287293

294+
let end = case bar.state.finished {
295+
True -> "\n"
296+
False -> ""
297+
}
298+
288299
io.print_error(
289300
codes.hide_cursor_code
290301
<> codes.clear_line_code
291302
<> codes.return_line_start_code
292303
<> bar.left
293304
<> fill
294-
<> bar.right,
305+
<> bar.right
306+
<> end,
295307
)
296308
}
297309

@@ -356,3 +368,69 @@ fn get_finished_fill(fill: StringBuilder, bar: ProgressStyle) -> StringBuilder {
356368
False -> string_builder.append(fill, bar.fill.char)
357369
}
358370
}
371+
372+
/// Map an iterator to a function with a bar that ticks every run of the
373+
/// function.
374+
///
375+
/// <details>
376+
/// <summary>Example:<summary>
377+
///
378+
/// ```gleam
379+
/// import glitzer/progress
380+
///
381+
/// fn example(bar) {
382+
/// iterator.range(0, 100)
383+
/// |> progress.map_iterator(fn(bar, element) {
384+
/// progress.print_bar(bar)
385+
/// // do some heavy calculations here >:)
386+
/// })
387+
/// }
388+
/// ```
389+
pub fn map_iterator(
390+
over i: Iterator(a),
391+
bar bar: ProgressStyle,
392+
with fun: fn(ProgressStyle, a) -> b,
393+
) -> Iterator(b) {
394+
iterator.index(i)
395+
|> iterator.map(fn(pair) {
396+
let #(el, i) = pair
397+
tick_bar_by_i(bar, i)
398+
|> fun(el)
399+
})
400+
}
401+
402+
fn tick_bar_by_i(bar, i) -> ProgressStyle {
403+
case i > 0 {
404+
True -> tick_bar_by_i(tick(bar), i - 1)
405+
False -> bar
406+
}
407+
}
408+
409+
pub fn map2_iterator(
410+
iterator1 i1: Iterator(a),
411+
iterator2 i2: Iterator(b),
412+
bar bar: ProgressStyle,
413+
with fun: fn(ProgressStyle, a, b) -> c,
414+
) -> Iterator(c) {
415+
iterator.zip(i1, i2)
416+
|> iterator.index
417+
|> iterator.map(fn(pair) {
418+
let #(pair, i) = pair
419+
let #(el1, el2) = pair
420+
tick_bar_by_i(bar, i)
421+
|> fun(el1, el2)
422+
})
423+
}
424+
425+
pub fn each_iterator(
426+
over i: Iterator(a),
427+
bar bar: ProgressStyle,
428+
with fun: fn(ProgressStyle, a) -> b,
429+
) -> Nil {
430+
iterator.index(i)
431+
|> iterator.each(fn(pair) {
432+
let #(el, i) = pair
433+
tick_bar_by_i(bar, i)
434+
|> fun(el)
435+
})
436+
}

0 commit comments

Comments
 (0)