@@ -2,7 +2,8 @@ import type { Denops } from "https://deno.land/x/denops_core@v3.0.1/mod.ts";
2
2
import * as autocmd from "../autocmd/mod.ts" ;
3
3
import * as batch from "../batch/mod.ts" ;
4
4
import * as fn from "../function/mod.ts" ;
5
- import * as helper from "../helper/mod.ts" ;
5
+ import * as vars from "../variable/mod.ts" ;
6
+ import { execute } from "../helper/mod.ts" ;
6
7
import * as unknownutil from "https://deno.land/x/unknownutil@v2.0.0/mod.ts" ;
7
8
import {
8
9
assertFileFormat ,
@@ -12,6 +13,81 @@ import {
12
13
splitText ,
13
14
} from "./fileformat.ts" ;
14
15
import { tryDecode } from "./fileencoding.ts" ;
16
+ import { generateUniqueString } from "../util.ts" ;
17
+
18
+ const suffix = generateUniqueString ( ) ;
19
+
20
+ async function ensurePrerequisites ( denops : Denops ) : Promise < string > {
21
+ if ( await vars . g . get ( denops , `loaded_denops_std_buffer_${ suffix } ` ) ) {
22
+ return suffix ;
23
+ }
24
+ const script = `
25
+ let g:loaded_denops_std_buffer_${ suffix } = 1
26
+
27
+ function! DenopsStdBufferReload_${ suffix } (bufnr) abort
28
+ if bufnr('%') is# a:bufnr
29
+ edit
30
+ return
31
+ endif
32
+ let winid_saved = win_getid()
33
+ let winid = bufwinid(a:bufnr)
34
+ if winid is# -1
35
+ augroup denops_std_buffer_reload_${ suffix }
36
+ execute printf('autocmd! * <buffer=%d>', a:bufnr)
37
+ execute printf('autocmd BufEnter <buffer=%d> ++nested ++once edit', a:bufnr)
38
+ augroup END
39
+ return
40
+ endif
41
+ keepjumps keepalt call win_gotoid(winid)
42
+ try
43
+ edit
44
+ finally
45
+ keepjumps keepalt call win_gotoid(winid_saved)
46
+ endtry
47
+ endfunction
48
+
49
+ function! DenopsStdBufferReplace_${ suffix } (bufnr, repl, fileformat, fileencoding) abort
50
+ let modified = getbufvar(a:bufnr, '&modified')
51
+ let modifiable = getbufvar(a:bufnr, '&modifiable')
52
+ let foldmethod = getbufvar(a:bufnr, '&foldmethod')
53
+ call setbufvar(a:bufnr, '&modifiable', 1)
54
+ call setbufvar(a:bufnr, '&foldmethod', 'manual')
55
+ if a:fileformat isnot# v:null
56
+ call setbufvar(a:bufnr, '&fileformat', a:fileformat)
57
+ endif
58
+ if a:fileencoding isnot# v:null
59
+ call setbufvar(a:bufnr, '&fileencoding', a:fileencoding)
60
+ endif
61
+ call setbufline(a:bufnr, 1, a:repl)
62
+ call deletebufline(a:bufnr, len(a:repl) + 1, '$')
63
+ call setbufvar(a:bufnr, '&modified', modified)
64
+ call setbufvar(a:bufnr, '&modifiable', modifiable)
65
+ call setbufvar(a:bufnr, '&foldmethod', foldmethod)
66
+ endfunction
67
+
68
+ function! DenopsStdBufferConcreteRestore_${ suffix } () abort
69
+ if !exists('b:denops_std_buffer_concrete_cache_${ suffix } ')
70
+ return
71
+ endif
72
+ call DenopsStdBufferReplace_${ suffix } (
73
+ \\ bufnr('%'),
74
+ \\ b:denops_std_buffer_concrete_cache_${ suffix } .content,
75
+ \\ v:null,
76
+ \\ v:null,
77
+ \\)
78
+ let &filetype = b:denops_std_buffer_concrete_cache_${ suffix } .filetype
79
+ endfunction
80
+
81
+ function! DenopsStdBufferConcreteStore_${ suffix } () abort
82
+ let b:denops_std_buffer_concrete_cache_${ suffix } = {
83
+ \\ 'filetype': &filetype,
84
+ \\ 'content': getline(1, '$'),
85
+ \\}
86
+ endfunction
87
+ ` ;
88
+ await execute ( denops , script ) ;
89
+ return suffix ;
90
+ }
15
91
16
92
export type OpenOptions = {
17
93
mods ?: string ;
@@ -35,25 +111,35 @@ export async function open(
35
111
* Edit a buffer
36
112
*/
37
113
export async function reload ( denops : Denops , bufnr : number ) : Promise < void > {
38
- await helper . load ( denops , new URL ( "./buffer.vim" , import . meta . url ) ) ;
114
+ const suffix = await ensurePrerequisites ( denops ) ;
39
115
await denops . cmd (
40
- "call timer_start(0, { -> DenopsStdBufferV1Reload(bufnr) })" ,
41
- {
42
- bufnr,
43
- } ,
116
+ `call timer_start(0, { -> DenopsStdBufferReload_${ suffix } (bufnr) })` ,
117
+ { bufnr } ,
44
118
) ;
45
119
}
46
120
121
+ export type ReplaceOptions = {
122
+ fileformat ?: string ;
123
+ fileencoding ?: string ;
124
+ } ;
125
+
47
126
/**
48
127
* Replace the buffer content
49
128
*/
50
129
export async function replace (
51
130
denops : Denops ,
52
131
bufnr : number ,
53
132
repl : string [ ] ,
133
+ options : ReplaceOptions = { } ,
54
134
) : Promise < void > {
55
- await helper . load ( denops , new URL ( "./buffer.vim" , import . meta. url ) ) ;
56
- await denops . call ( "DenopsStdBufferV1Replace" , bufnr , repl ) ;
135
+ const suffix = await ensurePrerequisites ( denops ) ;
136
+ await denops . call (
137
+ `DenopsStdBufferReplace_${ suffix } ` ,
138
+ bufnr ,
139
+ repl ,
140
+ options . fileformat ?? null ,
141
+ options . fileencoding ?? null ,
142
+ ) ;
57
143
}
58
144
59
145
export type AssignOptions = {
@@ -98,12 +184,9 @@ export async function assign(
98
184
findFileFormat ( text , fileformats ) ?? fileformat ;
99
185
const preprocessor = options . preprocessor ?? ( ( v : string [ ] ) => v ) ;
100
186
const repl = preprocessor ( splitText ( text , ff ) ) ;
101
- await modifiable ( denops , bufnr , async ( ) => {
102
- await batch . batch ( denops , async ( denops ) => {
103
- await fn . setbufvar ( denops , bufnr , "&fileformat" , ff ) ;
104
- await fn . setbufvar ( denops , bufnr , "&fileencoding" , enc ) ;
105
- await replace ( denops , bufnr , repl ) ;
106
- } ) ;
187
+ await replace ( denops , bufnr , repl , {
188
+ fileformat : ff ,
189
+ fileencoding : enc ,
107
190
} ) ;
108
191
}
109
192
@@ -119,30 +202,30 @@ export async function concrete(
119
202
denops : Denops ,
120
203
bufnr : number ,
121
204
) : Promise < void > {
122
- await helper . load ( denops , new URL ( "./buffer.vim" , import . meta . url ) ) ;
205
+ const suffix = await ensurePrerequisites ( denops ) ;
123
206
await batch . batch ( denops , async ( denops ) => {
124
207
await autocmd . group (
125
208
denops ,
126
- "denops_std_buffer_v1_concrete" ,
209
+ `denops_std_buffer_concrete_ ${ suffix } ` ,
127
210
( helper ) => {
128
211
const pat = `<buffer=${ bufnr } >` ;
129
212
helper . remove ( "*" , pat ) ;
130
213
helper . define (
131
214
"BufWriteCmd" ,
132
215
pat ,
133
- " call DenopsStdBufferV1ConcreteStore()" ,
216
+ ` call DenopsStdBufferConcreteStore_ ${ suffix } ()` ,
134
217
) ;
135
218
helper . define (
136
219
"BufReadCmd" ,
137
220
pat ,
138
- " call DenopsStdBufferV1ConcreteRestore()" ,
221
+ ` call DenopsStdBufferConcreteRestore_ ${ suffix } ()` ,
139
222
{
140
223
nested : true ,
141
224
} ,
142
225
) ;
143
226
} ,
144
227
) ;
145
- await denops . call ( "DenopsStdBufferV1ConcreteStore" ) ;
228
+ await denops . call ( `DenopsStdBufferConcreteStore_ ${ suffix } ` ) ;
146
229
} ) ;
147
230
}
148
231
0 commit comments