diff --git a/lib/keybind.c b/lib/keybind.c
index 7957769..eedea6b 100644
a
|
b
|
static name_keymap_t command_names[] = { |
353 | 353 | {"HunkPrev", CK_HunkPrev}, |
354 | 354 | {"EditOther", CK_EditOther}, |
355 | 355 | {"Merge", CK_Merge}, |
| 356 | {"MergeOther", CK_MergeOther}, |
356 | 357 | #endif /* USE_DIFF_VIEW */ |
357 | 358 | |
358 | 359 | {NULL, CK_IgnoreKey} |
diff --git a/lib/keybind.h b/lib/keybind.h
index 1258b44..5bfb81b 100644
a
|
b
|
enum |
328 | 328 | CK_HunkNext, |
329 | 329 | CK_HunkPrev, |
330 | 330 | CK_EditOther, |
331 | | CK_Merge |
| 331 | CK_Merge, |
| 332 | CK_MergeOther |
332 | 333 | }; |
333 | 334 | |
334 | 335 | /*** structures declarations (and typedefs of structures)*****************************************/ |
diff --git a/src/diffviewer/internal.h b/src/diffviewer/internal.h
index bdd2c29..60e7e21 100644
a
|
b
|
typedef struct WDiff |
84 | 84 | char *label[2]; |
85 | 85 | FBUF *f[2]; |
86 | 86 | const char *backup_sufix; |
87 | | gboolean merged; |
| 87 | gboolean merged[2]; |
88 | 88 | GArray *a[2]; |
89 | 89 | GPtrArray *hdiff; |
90 | 90 | int ndiff; /* number of hunks */ |
diff --git a/src/diffviewer/ydiff.c b/src/diffviewer/ydiff.c
index 538751a..8146ec9 100644
a
|
b
|
get_current_hunk (WDiff * dview, int *start_line1, int *end_line1, int *start_li |
2061 | 2061 | } |
2062 | 2062 | |
2063 | 2063 | static void |
2064 | | dview_remove_hunk (WDiff * dview, FILE * merge_file, int from1, int to1) |
| 2064 | dview_remove_hunk (WDiff * dview, FILE * merge_file, int from1, int to1, int other) |
2065 | 2065 | { |
2066 | 2066 | int line; |
2067 | 2067 | char buf[BUF_10K]; |
2068 | 2068 | FILE *f0; |
2069 | | f0 = fopen (dview->file[0], "r"); |
| 2069 | f0 = fopen (dview->file[other], "r"); |
2070 | 2070 | line = 0; |
2071 | 2071 | while (fgets (buf, sizeof (buf), f0) != NULL && line < from1 - 1) |
2072 | 2072 | { |
… |
… |
dview_remove_hunk (WDiff * dview, FILE * merge_file, int from1, int to1) |
2083 | 2083 | } |
2084 | 2084 | |
2085 | 2085 | static void |
2086 | | dview_add_hunk (WDiff * dview, FILE * merge_file, int from1, int from2, int to2) |
| 2086 | dview_add_hunk (WDiff * dview, FILE * merge_file, int from1, int from2, int to2, int other) |
2087 | 2087 | { |
2088 | 2088 | int line; |
2089 | 2089 | char buf[BUF_10K]; |
2090 | 2090 | FILE *f0; |
2091 | 2091 | FILE *f1; |
2092 | | f0 = fopen (dview->file[0], "r"); |
2093 | | f1 = fopen (dview->file[1], "r"); |
| 2092 | f0 = fopen (dview->file[other], "r"); |
| 2093 | f1 = fopen (dview->file[1-other], "r"); |
2094 | 2094 | line = 0; |
2095 | 2095 | while (fgets (buf, sizeof (buf), f0) != NULL && line < from1 - 1) |
2096 | 2096 | { |
… |
… |
dview_add_hunk (WDiff * dview, FILE * merge_file, int from1, int from2, int to2) |
2113 | 2113 | } |
2114 | 2114 | |
2115 | 2115 | static void |
2116 | | dview_replace_hunk (WDiff * dview, FILE * merge_file, int from1, int to1, int from2, int to2) |
| 2116 | dview_replace_hunk (WDiff * dview, FILE * merge_file, int from1, int to1, int from2, int to2, int other) |
2117 | 2117 | { |
2118 | 2118 | int line1, line2; |
2119 | 2119 | char buf[BUF_10K]; |
2120 | 2120 | FILE *f0; |
2121 | 2121 | FILE *f1; |
2122 | | f0 = fopen (dview->file[0], "r"); |
2123 | | f1 = fopen (dview->file[1], "r"); |
| 2122 | f0 = fopen (dview->file[other], "r"); |
| 2123 | f1 = fopen (dview->file[1-other], "r"); |
2124 | 2124 | line1 = 0; |
2125 | 2125 | while (fgets (buf, sizeof (buf), f0) != NULL && line1 < from1 - 1) |
2126 | 2126 | { |
… |
… |
dview_replace_hunk (WDiff * dview, FILE * merge_file, int from1, int to1, int fr |
2145 | 2145 | } |
2146 | 2146 | |
2147 | 2147 | static void |
2148 | | do_merge_hunk (WDiff * dview) |
| 2148 | do_merge_hunk (WDiff * dview, int other) |
2149 | 2149 | { |
2150 | 2150 | int from1, to1, from2, to2; |
2151 | 2151 | int res; |
2152 | 2152 | int hunk; |
2153 | 2153 | |
2154 | | hunk = get_current_hunk (dview, &from1, &to1, &from2, &to2); |
| 2154 | if (other) |
| 2155 | hunk = get_current_hunk (dview, &from2, &to2, &from1, &to1); |
| 2156 | else |
| 2157 | hunk = get_current_hunk (dview, &from1, &to1, &from2, &to2); |
2155 | 2158 | if (hunk > 0) |
2156 | 2159 | { |
2157 | 2160 | int merge_file_fd; |
2158 | 2161 | FILE *merge_file; |
2159 | 2162 | vfs_path_t *merge_file_name_vpath = NULL; |
2160 | 2163 | |
2161 | | if (!dview->merged) |
| 2164 | if (!dview->merged[other]) |
2162 | 2165 | { |
2163 | | dview->merged = mc_util_make_backup_if_possible (dview->file[0], "~~~"); |
2164 | | if (!dview->merged) |
| 2166 | dview->merged[other] = mc_util_make_backup_if_possible (dview->file[other], "~~~"); |
| 2167 | if (!dview->merged[other]) |
2165 | 2168 | { |
2166 | 2169 | message (D_ERROR, MSG_ERROR, |
2167 | 2170 | _("Cannot create backup file\n%s%s\n%s"), |
2168 | | dview->file[0], "~~~", unix_error_string (errno)); |
| 2171 | dview->file[other], "~~~", unix_error_string (errno)); |
2169 | 2172 | return; |
2170 | 2173 | } |
2171 | 2174 | |
… |
… |
do_merge_hunk (WDiff * dview) |
2184 | 2187 | switch (hunk) |
2185 | 2188 | { |
2186 | 2189 | case DIFF_DEL: |
2187 | | dview_remove_hunk (dview, merge_file, from1, to1); |
| 2190 | if (other) |
| 2191 | dview_add_hunk (dview, merge_file, from1, from2, to2, other); |
| 2192 | else |
| 2193 | dview_remove_hunk (dview, merge_file, from1, to1, other); |
2188 | 2194 | break; |
2189 | 2195 | case DIFF_ADD: |
2190 | | dview_add_hunk (dview, merge_file, from1, from2, to2); |
| 2196 | if (other) |
| 2197 | dview_remove_hunk (dview, merge_file, from1, to1, other); |
| 2198 | else |
| 2199 | dview_add_hunk (dview, merge_file, from1, from2, to2, other); |
2191 | 2200 | break; |
2192 | 2201 | case DIFF_CHG: |
2193 | | dview_replace_hunk (dview, merge_file, from1, to1, from2, to2); |
| 2202 | dview_replace_hunk (dview, merge_file, from1, to1, from2, to2, other); |
2194 | 2203 | break; |
2195 | 2204 | } |
2196 | 2205 | fflush (merge_file); |
2197 | 2206 | fclose (merge_file); |
2198 | | res = rewrite_backup_content (merge_file_name_vpath, dview->file[0]); |
| 2207 | res = rewrite_backup_content (merge_file_name_vpath, dview->file[other]); |
2199 | 2208 | mc_unlink (merge_file_name_vpath); |
2200 | 2209 | vfs_path_free (merge_file_name_vpath); |
2201 | 2210 | } |
… |
… |
dview_init (WDiff * dview, const char *args, const char *file1, const char *file |
2388 | 2397 | dview->label[1] = g_strdup (label2); |
2389 | 2398 | dview->f[0] = f[0]; |
2390 | 2399 | dview->f[1] = f[1]; |
| 2400 | dview->merged[0] = 0; |
| 2401 | dview->merged[1] = 0; |
2391 | 2402 | dview->hdiff = NULL; |
2392 | 2403 | dview->dsrc = dsrc; |
2393 | 2404 | dview->converter = str_cnv_from_term; |
… |
… |
dview_status (const WDiff * dview, int ord, int width, int c) |
2722 | 2733 | tty_gotoyx (0, c); |
2723 | 2734 | get_line_numbers (dview->a[ord], dview->skip_rows, &linenum, &lineofs); |
2724 | 2735 | |
2725 | | filename_width = width - 22; |
| 2736 | filename_width = width - 24; |
2726 | 2737 | if (filename_width < 8) |
2727 | 2738 | filename_width = 8; |
2728 | 2739 | |
… |
… |
dview_status (const WDiff * dview, int ord, int width, int c) |
2731 | 2742 | vfs_path_free (vpath); |
2732 | 2743 | buf = str_term_trim (path, filename_width); |
2733 | 2744 | if (ord == 0) |
2734 | | tty_printf ("%-*s %6d+%-4d Col %-4d ", filename_width, buf, linenum, lineofs, |
| 2745 | tty_printf ("%s%-*s %6d+%-4d Col %-4d ", dview->merged[ord] ? "* " : " ", filename_width, buf, linenum, lineofs, |
2735 | 2746 | dview->skip_cols); |
2736 | 2747 | else |
2737 | | tty_printf ("%-*s %6d+%-4d Dif %-4d ", filename_width, buf, linenum, lineofs, dview->ndiff); |
| 2748 | tty_printf ("%s%-*s %6d+%-4d Dif %-4d ", dview->merged[ord] ? "* " : " ", filename_width, buf, linenum, lineofs, dview->ndiff); |
2738 | 2749 | g_free (path); |
2739 | 2750 | } |
2740 | 2751 | |
… |
… |
static gboolean |
2875 | 2886 | dview_save (WDiff * dview) |
2876 | 2887 | { |
2877 | 2888 | gboolean res = TRUE; |
2878 | | if (!dview->merged) |
2879 | | return res; |
2880 | | res = mc_util_unlink_backup_if_possible (dview->file[0], "~~~"); |
2881 | | dview->merged = !res; |
| 2889 | if (dview->merged[0]) { |
| 2890 | res = mc_util_unlink_backup_if_possible (dview->file[0], "~~~"); |
| 2891 | dview->merged[0] = !res; |
| 2892 | } |
| 2893 | if (dview->merged[1]) { |
| 2894 | res = mc_util_unlink_backup_if_possible (dview->file[1], "~~~"); |
| 2895 | dview->merged[1] = !res; |
| 2896 | } |
2882 | 2897 | return res; |
2883 | 2898 | } |
2884 | 2899 | |
… |
… |
dview_ok_to_exit (WDiff * dview) |
2954 | 2969 | gboolean res = TRUE; |
2955 | 2970 | int act; |
2956 | 2971 | |
2957 | | if (!dview->merged) |
| 2972 | if (!dview->merged[0] && !dview->merged[1]) |
2958 | 2973 | return res; |
2959 | 2974 | |
2960 | 2975 | act = query_dialog (_("Quit"), !mc_global.midnight_shutdown ? |
2961 | | _("File was modified. Save with exit?") : |
2962 | | _("Midnight Commander is being shut down.\nSave modified file?"), |
| 2976 | _("File(s) was modified. Save with exit?") : |
| 2977 | _("Midnight Commander is being shut down.\nSave modified file(s)?"), |
2963 | 2978 | D_NORMAL, 2, _("&Yes"), _("&No")); |
2964 | 2979 | |
2965 | 2980 | /* Esc is No */ |
… |
… |
dview_ok_to_exit (WDiff * dview) |
2978 | 2993 | case 1: /* No */ |
2979 | 2994 | if (mc_util_restore_from_backup_if_possible (dview->file[0], "~~~")) |
2980 | 2995 | res = mc_util_unlink_backup_if_possible (dview->file[0], "~~~"); |
| 2996 | if (mc_util_restore_from_backup_if_possible (dview->file[1], "~~~")) |
| 2997 | res = mc_util_unlink_backup_if_possible (dview->file[1], "~~~"); |
2981 | 2998 | /* fall through */ |
2982 | 2999 | default: |
2983 | 3000 | res = TRUE; |
… |
… |
dview_execute_cmd (WDiff * dview, unsigned long command) |
3061 | 3078 | dview_edit (dview, dview->ord); |
3062 | 3079 | break; |
3063 | 3080 | case CK_Merge: |
3064 | | do_merge_hunk (dview); |
| 3081 | do_merge_hunk (dview, 0); |
| 3082 | dview_redo (dview); |
| 3083 | break; |
| 3084 | case CK_MergeOther: |
| 3085 | do_merge_hunk (dview, 1); |
3065 | 3086 | dview_redo (dview); |
3066 | 3087 | break; |
3067 | 3088 | case CK_EditOther: |
… |
… |
static char * |
3275 | 3296 | dview_get_title (const Dlg_head * h, size_t len) |
3276 | 3297 | { |
3277 | 3298 | const WDiff *dview = (const WDiff *) find_widget_type (h, dview_callback); |
3278 | | const char *modified = dview->merged ? " (*) " : " "; |
| 3299 | const char *modified = " (*) "; |
| 3300 | const char *notmodified = " "; |
3279 | 3301 | size_t len1; |
3280 | 3302 | GString *title; |
3281 | 3303 | |
… |
… |
dview_get_title (const Dlg_head * h, size_t len) |
3283 | 3305 | |
3284 | 3306 | title = g_string_sized_new (len); |
3285 | 3307 | g_string_append (title, _("Diff:")); |
3286 | | g_string_append (title, modified); |
| 3308 | g_string_append (title, dview->merged[0] ? modified : notmodified); |
3287 | 3309 | g_string_append (title, str_term_trim (dview->label[0], len1)); |
3288 | 3310 | g_string_append (title, " | "); |
| 3311 | g_string_append (title, dview->merged[1] ? modified : notmodified); |
3289 | 3312 | g_string_append (title, str_term_trim (dview->label[1], len1)); |
3290 | 3313 | |
3291 | 3314 | return g_string_free (title, FALSE); |
diff --git a/src/keybind-defaults.c b/src/keybind-defaults.c
index 75ae855..9d3ae1b 100644
a
|
b
|
static const global_keymap_ini_t default_diff_keymap[] = { |
525 | 525 | {"Edit", "f4"}, |
526 | 526 | {"EditOther", "f14"}, |
527 | 527 | {"Merge", "f5"}, |
| 528 | {"MergeOther", "f15"}, |
528 | 529 | {"Search", "f7"}, |
529 | 530 | {"SearchContinue", "f17"}, |
530 | 531 | {"Options", "f9"}, |