notepad++ select hyphenated text - text-editor

I could'nt find a solution to a problem that has been hindering the use of notepad++.
When you double click text to highlight that text and others like it, camelCase or under_score words work great, but when hyphen-words-are-clicked this does not treat it as a single word and only highlights the segment between the "-".
question: how can you customize notepad++ so that hyphenated words are treated as single words? or does anyone know a text editor that does this?
saw this, but not sure how to implement it: http://sourceforge.net/apps/mediawiki/notepad-plus/index.php?title=Word_Customisation
this was really helpful: Where are the recorded macros stored in Notepad++?

Notepad++ rely on Scintilla for word selection. As caoanan noticed in his answer, Scintilla can be configured with the SCI_SETWORDCHARS variable. You can set this variable in Notepad++ with a simple NppExec script:
Install NppExec
Menu Plugins -> plugin Manager -> Show Plugin Manager
locate NppExec, check the box and hit Install
Create the script
Menu Plugins -> NppExec -> Execute ...
write this code (you can add other characters, like .$## at the end of the list):
NPP_CONSOLE 0
sci_sendmsg SCI_SETWORDCHARS 0 "CDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_-"
hit Save...
You can now execute it by pressing OK
(optionnal) Execute when Notepad++ starts
Menu Plugins -> NppExec -> Advanced Options...
Choose your script in the Execute this script when Notepad++ starts drop down

2018
I tried with the published solutions but when I move to another file I have to run the script again every time. So I did this way, in the menu:
Settings > Preferences > Delimiter
select:
Add you character as part of word
insert hyphen:
-
and it worked.

I met with the same problem when editing Lisp/Scheme source codes with Notepad++.
The cure lies in the underlying Scintilla library (SciLexer.dll).
I've tried in a "blunt" way -- hack the code and rebuild SciLexer.dll.
Note the '-' added to the following code
CharClassify.cxx
void CharClassify::SetDefaultCharClasses(bool includeWordClass) {
// Initialize all char classes to default values
for (int ch = 0; ch < 256; ch++) {
if (ch == '\r' || ch == '\n')
charClass[ch] = ccNewLine;
else if (ch < 0x20 || ch == ' ')
charClass[ch] = ccSpace;
else if (includeWordClass && (ch >= 0x80 || isalnum(ch) || ch == '_' || ch == '-'))
charClass[ch] = ccWord;
else
charClass[ch] = ccPunctuation;
}
}
Or, the "smart" way, as mentioned at ScintillaDoc.html
SCI_SETWORDCHARS(<unused>, const char *characters)
Scintilla has several functions that operate on words, which are
defined to be contiguous sequences of characters from a particular set
of characters. This message defines which characters are members of
that set. The character sets are set to default values before
processing this function. For example, if you don't allow '_' in your
set of characters use: SCI_SETWORDCHARS(0,abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789");

http://sourceforge.net/p/notepad-plus/discussion/1290590/thread/39ba5cd8/
Install Npp_Exec plugin and copy the string from this thread adding the signs you want Npp considers as part of a word.

I don't know that option in Notepad++ yet. Since, you've asked about any other text editor that does so, I would recommend you to use Sublime Text. It's a really cool text editor with lots of smart features. I bet you'll love it. By default, it does not treat the hyphenated words as a single word. But it's way too easy to customize the setting for that. All you need to do is go to 'Preference-> Setting-Default', where you'll find the following setting:
"word_separators": "./\\()\"'-:,.;<>~!##$%^&*|+=[]{}`~?",
From there, just remove the hyphen and we're done!

A workaround is to:
In the Find window, set the text to find to a space
In the Shortcut Mapper (Main Menu section) assign "Find Next" to Ctrl+Right and "Find Previous" to Ctrl+Left
Now, so long as the search text is only a space, it will effectively be the only delimiter. If you need other delimiters, for instance comma and period, set the Find text to [ ,.].

If you don't have admin rights and no Plugin Mgr, you can install most plugins by downloading a dll/zip file and saving the dll to the 'plugins' sub-folder under your npp install. Then restart npp.

Related

how to delete til a char in the next lines.

I have the following text layout. and I want to delete from ON to the ";" I tried to use "dt;", but it said it can't find ";", looks like "t" only try to find the char in the same line, possible to find the next lines?
INNER JOIN () a *cursor* ON f.StoreID = a.StoreID
AND f.UPC = a.UPC
AND f.type = 'tom' ;
...other text...
You will have to search for it and delete up to it using d/;<CR>. (<CR> is carriage return: pressing the return/enter key) Using d with a search behaves like using t with d. It will delete up to that character (or word if using a search). This is the behavior you want. If you want to also delete the ; you should use v/;<CR>d to select all of it and then delete it.
You are correct that t, T, f and F all only look at the current line.
Zach's answer is the correct way to do this with vanilla vim however there are several plugins that you could use if you don't wish to use search.
I'd recommend you take a look at vim-sneak: Sneak is a minimalist, versatile Vim motion plugin that jumps to any location specified by two characters. Using sneak you would use dz;<cr> to delete to the next occurrence of ;. This has the advantage of not leaving all other ; characters highlighted.
The vim-sneak README also list a bunch of similar plugins.
"dt;" is only usefull in one line.I don't think there is a way to do this unless you define a macro, which makes no sense , because you can't decide delete to which ";", next line or next next line .I think you type D with your cursor on ON, then move to nextline and type dd.Use simple cmd to compose a strong cmd.Just like the unix, keep it simple。
I would add another option, using easyMotion plugin.
you can d<leader><leader>f; then choose which ; you want to delete to. pretty handy.

Substitute for vim replace in Sublime

I'm looking for a replacement for vim's "replace with character" command--specifically, I want to be able to select some text and replace each character with some character that I type (difficulty: No "vintage" mode)
Example:
Starting with
I am some text with an arbitrary number: 12358998281
I want an easy way to select 12358998281 and turn it into 99999999999, to make the result
I am some text with an arbitrary number: 99999999999
(in vim, this would be done by moving the cursor to the beginning of 12358998281, selecting with ve, then pressing r9)
I can do this by selecting the text, bringing up the "find" dialog, making sure "in selection" and "by regex" are enabled, searching for ., then typing my character into the resulting multiselect. This is incredibly laborious, however, and it prevents me from doing this process on a multiselect (for example, if 12358998281 exists in multiple parts of the file, I might want to quickly replace all instances of it with 99999999999, rather than performing the process above, getting the substitution, copying it to the clipboard, and then replacing with that).
Does Sublime have a command that acts like vim's "replace" that I can bind to something, or do I have to write a macro to get what I need? Or, am I approaching this from entirely the wrong direction?
A more generalized way of thinking of this is "how can I break a select into a multiselect on all characters", if that helps.
By using this package https://sublime.wbond.net/packages/RegReplace you can create regex patterns and bind them to shortcuts.
Also if there are multiple occurrences of one word, you can put cursor on whatever part of the word and press CTRL+D multiple times. One CTRL+D press will select the word under the cursor, every other press will select next occurrence of the word.
You could also use https://sublime.wbond.net/packages/Expand%20Selection%20to%20Whitespace to expand the selection to whitespace if your word contain some random characters, and then press CTDL+D to select next occurrences of the word.
Edit: With the package regex shortcuts indeed you have to create regexes before binding them. But the CTRL+D does work without it.
I don't see a problem with using "Expand selection to whitespace" and than doing the CTRL+D as I wrote in the answer.
I've checked the usage of visual as you wrote in the question and this solution seems much faster to do. You don't have to place cursor in the beggining of the word as It can be whereever in the word and no find/replace is needed, since you'll multiselect all occurrences by holding CTRL+D for a sec and You'll be free to edit it.
You can also use https://sublime.wbond.net/packages/Expand%20Selection%20to%20Quotes to select text inside quote and combine it with CTRL+D if standard CTRL+D doesn't work with some text, or if select to whitespace selects too much text.
I ended up solving this with a simple (if inelegant) plugin:
import sublime_plugin
import sublime
class MultiSelectWithinSelectedCommand(sublime_plugin.TextCommand):
def run(self, edit):
selection = self.view.sel()
new_regions = []
for selected_region in selection:
if selected_region.empty():
selection.add(self.view.word(selected_region))
for selected_region in selection:
if selected_region.a > selected_region.b:
region_begin = selected_region.b
else:
region_begin = selected_region.a
for pos in range(selected_region.size()):
subregion_begin = region_begin + pos
subregion_end = subregion_begin + 1
new_regions.append(sublime.Region(subregion_begin, subregion_end))
selection.clear()
selection.add_all(new_regions)
Once I've stuck this in my plugins directory, I would bind a command in the keymap file like usual:
{ "keys": ["alt+f"], "command": "multi_select_within_selected" }
(with alt+f chosen arbitrarily), and lo, multi-select on all selected characters with a keypress (after which, I can press my replacement character).

Bulk replacement of strings in single text file (Notepad++)

I am using Notepad++ to edit a text file that has been poorly encoded log. The program didn't take into account the AZERTY keyboard layout of the user. The result is a text file as follows (example I made up)
Hi guysm this is Qqron<
I zonder zhen ze cqn go to the szi;;ing pool together
:y phone nu;ber is !%%)#!####(
Cqll ;e/
I need to make bulk replacement of characters as follows
a > q
q > a
[/0] > 0
! > 1
and a few others
Is it possible to create a table of characters to be replaced ? I'm a bit of a beginner and I don't know whether Notepad++ allows to run scripts
Notepad++ has a macro recorder, but macros can't be written in any documented embedded language. You could potentially record a macro that does 70 or so search and replace operations. See this explanation. There is some information on "hacking" the macro language here.
Clearly Notepad++ was not meant for this task. The Python solutions are okay, but Perl was meant originally for stuff exactly like this. Here's a one-liner. This is for Windows. In bash/Linux, replace the double quotes with single ones.
perl -n -e "tr/aqAQzwZW;:!##$%^&*()m\/</qaQAwzWZmM1234567890:?./;print"
It will do what #kreativitea's solution does (I used his translation strings), reading the standard input and printing to standard output.
I don't know about Notepad++. But if you have python installed in your machine, you can you this little script.
source = """Hi guysm this is Qqron<
I zonder zhen ze cqn go to the szi;;ing pool together
:y phone nu;ber is !%%)#!####(
Cqll ;e/"""
replace_dict = {'a': 'q', 'q': 'a', '[/0]': '0', '!': '1'}
target = ''
for char in source:
target_char = replace_dict.get(char)
if target_char:
target += target_char
else:
target += char
print target
Just customize the replace_dict variable to suit your need.
So, there are quite a few different kinds of AZERTY layouts, so this isn't a complete answer. However, it does pass your test case, and does it as fast as any single character replacement can be done in python (unless you need to take unicode into account as well)
from string import maketrans
test = '''Hi guysm this is Qqron<
I zonder zhen ze cqn go to the szi;;ing pool together
:y phone nu;ber is !%%)#!####(
Cqll ;e/'''
# warning: not a full table.
table = maketrans('aqAQzwZW;:!##$%^&*()m/<', 'qaQAwzWZmM1234567890:?.')
test.translate(table)
So, as long as you find out what version of AZERTY your user is using, you should be okay. Just make sure to properly fill out the translation table with the details of the AZERTY implementation.

Remove/Add Line Breaks after Specific String using Sublime Text

Using Sublime Text 2 - Is it possible to insert a line break/text return after a specific String in a text file e.g. by using the Find ‣ Replace tool?
(Bonus question: Is it possible to remove all line breaks after a specific String)
Here's how you'd do it on a Mac:
Command+F > type string > Control+Command+G > ESC > Right Arrow > line break
and Windows/Linux (untested):
Control+F > type string > Alt+F3 > ESC > Right Arrow > line break
The important part being Control+Command+G to select all matches.
Once you've selected the text you're looking for, you can use the provided multiple cursors to do whatever text manipulation you want.
Protip: you can manually instantiate multiple cursors by using Command+click (or Control+click) to achieve similar results.
Using the Find - Replace tool, this can be accomplished in two different ways:
Click in the Replace field and press Ctrl + Enter to insert a newline (the field should resize but it doesn't, so it is hard to see the newline inserted).
Inside the Find - Replace tool, activate the S&R regex mode (first icon on the left .*, keyboard shortcut is Alt + Ctrl/Cmd + R to activate/deactivate it).
Type \n in the Replace field wherever you want to insert a newline.
Both solutions also work if you want to find newlines, just do it in the Find field.
Edit->Lines->Join Line (Ctrl+J)
You should probably use multiple cursors. See the unofficial documentation, or this nice tutorial. Here's some brief instructions to set you on your way:
Put the cursor on the string of interest.
Type Command+D (Mac) or Control+D (Windows/Linux) to select the current instance of the string.
Type Command+D (Mac) or Control+D (Windows/Linux) to select successive instances of the string.
Alternately, type Control+Command+G (Mac) or Control+Command+G to select all instances of your string.
Now you have multiple cursors, so insert or remove your newline as you please.
(type esc to exit multiple cursor mode.)
Have fun!

reformat in vim for a nice column layout

I have this dataset in a csv file
1.33570301776, 3.61194e-06, 7.24503e-06, -9.91572e-06, 1.25098e-05, 0.0102828, 0.010352, 0.0102677, 0.0103789, 0.00161604, 0.00167978, 0.00159998, 0.00182596, 0.0019804, 0.0133687, 0.010329, 0.00163437, 0.00191202, 0.0134425
1.34538754675, 3.3689e-06, 9.86066e-06, -9.12075e-06, 1.18058e-05, 0.00334344, 0.00342207, 0.00332897, 0.00345504, 0.00165532, 0.00170412, 0.00164234, 0.00441903, 0.00459294, 0.00449357, 0.00339737, 0.00166596, 0.00451926, 0.00455153
1.34808186291, -1.99011e-06, 6.53026e-06, -1.18909e-05, 9.52337e-06, 0.00158065, 0.00166529, 0.0015657, 0.0017022, 0.000740644, 0.00078635, 0.000730052, 0.00219736, 0.00238191, 0.00212762, 0.00163783, 0.000750669, 0.00230171, 0.00217917
As you can see, the numbers are formatted differently and misaligned. Is there a way in vim to quickly align the columns properly, so that the result is this
1.33570301776, 3.61194e-06, 7.24503e-06, -9.91572e-06, 1.25098e-05, 0.0102828, 0.010352, 0.0102677, 0.0103789, 0.00161604, 0.00167978, 0.00159998, 0.00182596, 0.0019804, 0.0133687, 0.010329, 0.00163437, 0.00191202, 0.0134425
1.34538754675, 3.3689e-06, 9.86066e-06, -9.12075e-06, 1.18058e-05, 0.00334344, 0.00342207, 0.00332897, 0.00345504,0.00165532, 0.00170412, 0.00164234, 0.00441903, 0.00459294, 0.00449357, 0.00339737, 0.00166596, 0.00451926, 0.00455153
1.34808186291, -1.99011e-06, 6.53026e-06, -1.18909e-05, 9.52337e-06, 0.00158065, 0.00166529, 0.0015657, 0.0017022, 0.000740644,0.00078635, 0.000730052,0.00219736, 0.00238191, 0.00212762, 0.00163783, 0.000750669,0.00230171, 0.00217917
That would be great to copy and paste sections with ctrl-v. Any hints?
If you're on some kind of UNIX (Linux, etc), you can cheat and filter it through the column(1) command.
:%!column -t
The above will parse on delimiters inside string literals which is wrong, so you will likely need pre-processing steps and specifying the delimiter for this file for example:
%!sed 's/","/\&/' | column -t -s '&'
Sometimes we want to align just two columns. In that case, we don't need any plugins and can use pure Vim functionality like this:
Choose a separator. In OP's post this is a comma, in my example this is =.
Add spaces before/after it. I use s/=/= ...spaces... / in visual selection for this.
Locate to the longest word and place cursor after it.
Remove all the extra whitespace using dw and vertical movement.
Example of this technique demonstrated below:
I don't find myself needing to align things often enough to install another plugin, so this was my preferred way of accomplishing it - especially that it doesn't require much thinking.
As sunny256 suggested, the column command is a great way of doing this on Unix/Linux machines, but if you want to do it in pure Vim (so that it can be used in Windows as well), the easiest way is to install the Align plugin and then do:
:%Align ,
:%s/\(\s\+\),\s/,\1/g
The first line aligns the entries on the commas and the second moves the comma so that it's flush with the preceding value. You may be able to use AlignCtrl to define a custom mapping that does the whole lot in one go, but I can never remember how to use it...
Edit
If you don't mind two spaces between entries and you want to do this in one command, you can also do:
:%Align ,\zs
This is a great answer using vim macros: https://stackoverflow.com/a/8363786/59384 - basically, you start recording a macro, format the first column, stop recording then repeat the macro for all remaining lines.
Copy/pasted from that answer:
qa0f:w100i <Esc>19|dwjq4#a
Note the single space after the 100i, and the <Esc> means "press escape"--don't type "<Esc>" literally.
Translation:
qa -- record macro in hotkey a
0 -- go to beginning of line
f: -- go to first : symbol
w -- go to next non-space character after the symbol
100i <Esc> -- insert 100 spaces
19| -- go to 19th column (value 19 figured out manually)
dw -- delete spaces until : symbol
j -- go to next line
q -- stop recording macro
4#a -- run the macro 4 times (for the remaining 4 lines)
We now also have the fabulous EasyAlign plugin, written by junegunn.
Demonstration GIF from its README:
Also, Tabularize is quite good http://vimcasts.org/episodes/aligning-text-with-tabular-vim/
You could use the csv.vim plugin.
:%ArrangeColumn
However, this will not do exactly what you have asked: it will right adjust the contents of cells, whereas you have your values aligned by the decimal point or by the first digit.
The plugin has many other useful commands for working with CSV files.
also if you have very long columns it can be handy to disable default wrapping
:set nowrap
:%!column -t
(note in debian you also have a further option for column -n which if you want to split multiple adjacent delimiters)
Here’s a pure Vim script answer, no plugins, no macros:
It might be most clear to start out with my problem’s solution as an example. I selected the lines of code I wanted to affect, then used the following command (recall that entering command mode from visual mode automatically prepends the “'<,'>”, so it acts on the visual range):
:'<,'>g``normal / "value<0d>D70|P`
Except I did NOT actually type “<0d>”. You can enter unprintable characters on the command line by pressing ctrl-v, then the key you want to type. “<0d>” is what is rendered on the command line after I typed ‘ctrl-v enter’. Here, it’s parsed by the “normal” command as the exit from “/” search mode. The cursor then jumps to “ value” in the current line.
Then we simply [D]elete the rest of the line, jump to column 70 (or whatever you need in your case), and [P]ut what we just deleted. This does mean we have to determine the width of the widest line, up to our search. If you haven’t put that information in your statusline, you can see the column of the cursor by entering the normal mode command ‘g ctrl-g’. Also note that jumping to a column that doesn’t exist requires the setting 'virtualedit'!
I left the search term for the :g(lobal) command empty, since we used a visual block and wanted to affect every line, but you can leave off using a visual selection (and the “'<,'>”) and put a search term there instead. Or combine a visual selection and a search term to narrow things more finely/easily.
Here’s something I learned recently: if you mess up on a complex command mode command, undo with ‘u’ (if it affected the buffer), then press “q:” to enter a special command history buffer that acts much like a conventional buffer. Edit any line and press enter, and the changed command is entered as a new command. Indispensable if you don’t want to have to stress over formulating everything perfectly the first time.
I just wrote tablign for this purpose. Install with
pip3 install tablign --user
Then simply mark the table in vim and do
:'<,'>:!tablign
Pretty old question, but I've recently availed myself of an excellent vim plugin that enables table formatting either on the fly or after-the-fact (as your use case requires):
https://github.com/dhruvasagar/vim-table-mode
I have this in my .vimrc.
command! CSV set nowrap | %s/,/,|/g | %!column -n -t -s "|"
This aligns the columns while keeping the comma, which may be needed later for correct reading. For example, with Python Pandas read_csv(..., skipinitialspace=True), thanks Pandas guys for this smart option, otherwise in vim %s/,\s\+/,/g. It may be easier if your column has the option --output-separator I guess, my doesn't and I'm not sure why (my man page for column says 2004, on ubuntu 18.04, not sure ubuntu will get a new version). Anyway, this works for me, and comment if you have any suggestions.
I made a cli tool written in Perl.
You can find it here: https://github.com/bas080/colcise

Resources